diff --git a/core/java/android/provider/Settings.java b/core/java/android/provider/Settings.java
index 30bcbf4..929466c 100644
--- a/core/java/android/provider/Settings.java
+++ b/core/java/android/provider/Settings.java
@@ -12162,7 +12162,7 @@
         /**
          * Defines global runtime overrides to window policy.
          *
-         * See {@link com.android.server.policy.PolicyControl} for value format.
+         * See {@link com.android.server.wm.PolicyControl} for value format.
          *
          * @hide
          */
diff --git a/core/java/android/view/IWindowManager.aidl b/core/java/android/view/IWindowManager.aidl
index c836c9e..308a000 100644
--- a/core/java/android/view/IWindowManager.aidl
+++ b/core/java/android/view/IWindowManager.aidl
@@ -271,7 +271,7 @@
     /**
      * Called by the status bar to notify Views of changes to System UI visiblity.
      */
-    oneway void statusBarVisibilityChanged(int visibility);
+    oneway void statusBarVisibilityChanged(int displayId, int visibility);
 
     /**
      * Called by System UI to notify of changes to the visibility of Recents.
diff --git a/core/proto/android/server/windowmanagerservice.proto b/core/proto/android/server/windowmanagerservice.proto
index b0dbaa0..99f096d 100644
--- a/core/proto/android/server/windowmanagerservice.proto
+++ b/core/proto/android/server/windowmanagerservice.proto
@@ -97,7 +97,7 @@
 message WindowManagerPolicyProto {
     option (.android.msg_privacy).dest = DEST_AUTOMATIC;
 
-    optional int32 last_system_ui_flags = 1;
+    optional int32 last_system_ui_flags = 1 [deprecated=true];
     enum UserRotationMode {
         USER_ROTATION_FREE = 0;
         USER_ROTATION_LOCKED = 1;
@@ -108,18 +108,18 @@
     optional bool screen_on_fully = 5;
     optional bool keyguard_draw_complete = 6;
     optional bool window_manager_draw_complete = 7;
-    optional string focused_app_token = 8;
-    optional IdentifierProto focused_window = 9;
-    optional IdentifierProto top_fullscreen_opaque_window = 10;
-    optional IdentifierProto top_fullscreen_opaque_or_dimming_window = 11;
+    optional string focused_app_token = 8 [deprecated=true];
+    optional IdentifierProto focused_window = 9 [deprecated=true];
+    optional IdentifierProto top_fullscreen_opaque_window = 10 [deprecated=true];
+    optional IdentifierProto top_fullscreen_opaque_or_dimming_window = 11 [deprecated=true];
     optional bool keyguard_occluded = 12;
     optional bool keyguard_occluded_changed = 13;
     optional bool keyguard_occluded_pending = 14;
-    optional bool force_status_bar = 15;
-    optional bool force_status_bar_from_keyguard = 16;
-    optional BarControllerProto status_bar = 17;
-    optional BarControllerProto navigation_bar = 18;
-    optional WindowOrientationListenerProto orientation_listener = 19;
+    optional bool force_status_bar = 15 [deprecated=true];
+    optional bool force_status_bar_from_keyguard = 16 [deprecated=true];
+    optional BarControllerProto status_bar = 17 [deprecated=true];
+    optional BarControllerProto navigation_bar = 18 [deprecated=true];
+    optional WindowOrientationListenerProto orientation_listener = 19 [deprecated=true];
     optional KeyguardServiceDelegateProto keyguard_delegate = 20;
 }
 
diff --git a/packages/SystemUI/shared/src/com/android/systemui/shared/system/WindowManagerWrapper.java b/packages/SystemUI/shared/src/com/android/systemui/shared/system/WindowManagerWrapper.java
index 3191d14..42e60aa 100644
--- a/packages/SystemUI/shared/src/com/android/systemui/shared/system/WindowManagerWrapper.java
+++ b/packages/SystemUI/shared/src/com/android/systemui/shared/system/WindowManagerWrapper.java
@@ -17,6 +17,9 @@
 package com.android.systemui.shared.system;
 
 import static android.view.Display.DEFAULT_DISPLAY;
+import static android.view.WindowManagerPolicyConstants.NAV_BAR_BOTTOM;
+import static android.view.WindowManagerPolicyConstants.NAV_BAR_LEFT;
+import static android.view.WindowManagerPolicyConstants.NAV_BAR_RIGHT;
 
 import android.app.WindowConfiguration;
 import android.graphics.Rect;
@@ -26,10 +29,6 @@
 import android.view.WindowManager;
 import android.view.WindowManagerGlobal;
 
-import static android.view.WindowManagerPolicyConstants.NAV_BAR_RIGHT;
-import static android.view.WindowManagerPolicyConstants.NAV_BAR_BOTTOM;
-import static android.view.WindowManagerPolicyConstants.NAV_BAR_LEFT;
-
 import com.android.systemui.shared.recents.view.AppTransitionAnimationSpecsFuture;
 import com.android.systemui.shared.recents.view.RecentsTransition;
 
@@ -179,6 +178,7 @@
      */
     public int getNavBarPosition() {
         try {
+            // TODO: Use WindowManagerService.getNavBarPosition(int displayId)
             return WindowManagerGlobal.getWindowManagerService().getNavBarPosition();
         } catch (RemoteException e) {
             Log.w(TAG, "Failed to get nav bar position");
diff --git a/packages/SystemUI/src/com/android/systemui/statusbar/phone/NavigationBarView.java b/packages/SystemUI/src/com/android/systemui/statusbar/phone/NavigationBarView.java
index 2f58ca1..5db43ea 100644
--- a/packages/SystemUI/src/com/android/systemui/statusbar/phone/NavigationBarView.java
+++ b/packages/SystemUI/src/com/android/systemui/statusbar/phone/NavigationBarView.java
@@ -904,6 +904,7 @@
         boolean isRtl = (getLayoutDirection() == View.LAYOUT_DIRECTION_RTL);
         int navBarPos = 0;
         try {
+            // TODO: Use WindowManagerService.getNavBarPosition(int displayId)
             navBarPos = WindowManagerGlobal.getWindowManagerService().getNavBarPosition();
         } catch (RemoteException e) {
             Slog.e(TAG, "Failed to get nav bar position.", e);
diff --git a/packages/SystemUI/src/com/android/systemui/statusbar/phone/StatusBar.java b/packages/SystemUI/src/com/android/systemui/statusbar/phone/StatusBar.java
index 45e924f..bdddf5b 100644
--- a/packages/SystemUI/src/com/android/systemui/statusbar/phone/StatusBar.java
+++ b/packages/SystemUI/src/com/android/systemui/statusbar/phone/StatusBar.java
@@ -2251,7 +2251,8 @@
     private void notifyUiVisibilityChanged(int vis) {
         try {
             if (mLastDispatchedSystemUiVisibility != vis) {
-                mWindowManagerService.statusBarVisibilityChanged(vis);
+                // TODO (b/117478341): Resolve one status bar/ navigation bar assumption
+                mWindowManagerService.statusBarVisibilityChanged(Display.DEFAULT_DISPLAY, vis);
                 mLastDispatchedSystemUiVisibility = vis;
             }
         } catch (RemoteException ex) {
diff --git a/services/core/java/com/android/server/policy/PhoneWindowManager.java b/services/core/java/com/android/server/policy/PhoneWindowManager.java
index 59c6d0a..3ba1155 100644
--- a/services/core/java/com/android/server/policy/PhoneWindowManager.java
+++ b/services/core/java/com/android/server/policy/PhoneWindowManager.java
@@ -20,13 +20,7 @@
 import static android.Manifest.permission.SYSTEM_ALERT_WINDOW;
 import static android.app.AppOpsManager.OP_SYSTEM_ALERT_WINDOW;
 import static android.app.AppOpsManager.OP_TOAST_WINDOW;
-import static android.app.WindowConfiguration.ACTIVITY_TYPE_HOME;
-import static android.app.WindowConfiguration.ACTIVITY_TYPE_STANDARD;
-import static android.app.WindowConfiguration.WINDOWING_MODE_FREEFORM;
-import static android.app.WindowConfiguration.WINDOWING_MODE_FULLSCREEN;
 import static android.app.WindowConfiguration.WINDOWING_MODE_SPLIT_SCREEN_PRIMARY;
-import static android.app.WindowConfiguration.WINDOWING_MODE_SPLIT_SCREEN_SECONDARY;
-import static android.app.WindowConfiguration.WINDOWING_MODE_UNDEFINED;
 import static android.content.Context.CONTEXT_RESTRICTED;
 import static android.content.Context.DISPLAY_SERVICE;
 import static android.content.Context.WINDOW_SERVICE;
@@ -35,61 +29,28 @@
 import static android.content.pm.PackageManager.FEATURE_WATCH;
 import static android.content.pm.PackageManager.PERMISSION_GRANTED;
 import static android.content.res.Configuration.EMPTY;
-import static android.content.res.Configuration.UI_MODE_TYPE_CAR;
-import static android.content.res.Configuration.UI_MODE_TYPE_MASK;
 import static android.os.Build.VERSION_CODES.M;
 import static android.os.Build.VERSION_CODES.O;
 import static android.provider.Settings.Secure.VOLUME_HUSH_OFF;
 import static android.view.Display.DEFAULT_DISPLAY;
 import static android.view.Display.INVALID_DISPLAY;
 import static android.view.Display.STATE_OFF;
-import static android.view.WindowManager.DOCKED_LEFT;
-import static android.view.WindowManager.DOCKED_RIGHT;
-import static android.view.WindowManager.DOCKED_TOP;
-import static android.view.WindowManager.INPUT_CONSUMER_NAVIGATION;
 import static android.view.WindowManager.LayoutParams.FIRST_APPLICATION_WINDOW;
 import static android.view.WindowManager.LayoutParams.FIRST_SUB_WINDOW;
 import static android.view.WindowManager.LayoutParams.FIRST_SYSTEM_WINDOW;
-import static android.view.WindowManager.LayoutParams.FLAG_ALLOW_LOCK_WHILE_SCREEN_ON;
-import static android.view.WindowManager.LayoutParams.FLAG_DRAWS_SYSTEM_BAR_BACKGROUNDS;
-import static android.view.WindowManager.LayoutParams.FLAG_FORCE_NOT_FULLSCREEN;
-import static android.view.WindowManager.LayoutParams.FLAG_FULLSCREEN;
-import static android.view.WindowManager.LayoutParams.FLAG_LAYOUT_ATTACHED_IN_DECOR;
-import static android.view.WindowManager.LayoutParams.FLAG_LAYOUT_INSET_DECOR;
-import static android.view.WindowManager.LayoutParams.FLAG_LAYOUT_IN_OVERSCAN;
-import static android.view.WindowManager.LayoutParams.FLAG_LAYOUT_IN_SCREEN;
-import static android.view.WindowManager.LayoutParams.FLAG_LAYOUT_NO_LIMITS;
 import static android.view.WindowManager.LayoutParams.FLAG_SHOW_WALLPAPER;
 import static android.view.WindowManager.LayoutParams.FLAG_SHOW_WHEN_LOCKED;
-import static android.view.WindowManager.LayoutParams.FLAG_TRANSLUCENT_NAVIGATION;
-import static android.view.WindowManager.LayoutParams.FLAG_TRANSLUCENT_STATUS;
 import static android.view.WindowManager.LayoutParams.LAST_APPLICATION_WINDOW;
 import static android.view.WindowManager.LayoutParams.LAST_SUB_WINDOW;
 import static android.view.WindowManager.LayoutParams.LAST_SYSTEM_WINDOW;
 import static android.view.WindowManager.LayoutParams.LAYOUT_IN_DISPLAY_CUTOUT_MODE_ALWAYS;
-import static android.view.WindowManager.LayoutParams.LAYOUT_IN_DISPLAY_CUTOUT_MODE_DEFAULT;
-import static android.view.WindowManager.LayoutParams.MATCH_PARENT;
-import static android.view.WindowManager.LayoutParams.PRIVATE_FLAG_ACQUIRES_SLEEP_TOKEN;
-import static android.view.WindowManager.LayoutParams.PRIVATE_FLAG_FORCE_DRAW_STATUS_BAR_BACKGROUND;
-import static android.view.WindowManager.LayoutParams.PRIVATE_FLAG_FORCE_STATUS_BAR_VISIBLE_TRANSPARENT;
-import static android.view.WindowManager.LayoutParams.PRIVATE_FLAG_INHERIT_TRANSLUCENT_DECOR;
 import static android.view.WindowManager.LayoutParams.PRIVATE_FLAG_IS_ROUNDED_CORNERS_OVERLAY;
-import static android.view.WindowManager.LayoutParams.PRIVATE_FLAG_IS_SCREEN_DECOR;
 import static android.view.WindowManager.LayoutParams.PRIVATE_FLAG_KEYGUARD;
 import static android.view.WindowManager.LayoutParams.PRIVATE_FLAG_SHOW_FOR_ALL_USERS;
-import static android.view.WindowManager.LayoutParams.PRIVATE_FLAG_STATUS_FORCE_SHOW_NAVIGATION;
 import static android.view.WindowManager.LayoutParams.PRIVATE_FLAG_SYSTEM_ERROR;
-import static android.view.WindowManager.LayoutParams.ROTATION_ANIMATION_CROSSFADE;
-import static android.view.WindowManager.LayoutParams.ROTATION_ANIMATION_JUMPCUT;
-import static android.view.WindowManager.LayoutParams.ROTATION_ANIMATION_ROTATE;
-import static android.view.WindowManager.LayoutParams.ROTATION_ANIMATION_SEAMLESS;
-import static android.view.WindowManager.LayoutParams.SOFT_INPUT_ADJUST_NOTHING;
-import static android.view.WindowManager.LayoutParams.SOFT_INPUT_ADJUST_RESIZE;
-import static android.view.WindowManager.LayoutParams.SOFT_INPUT_MASK_ADJUST;
 import static android.view.WindowManager.LayoutParams.TYPE_ACCESSIBILITY_OVERLAY;
 import static android.view.WindowManager.LayoutParams.TYPE_APPLICATION_OVERLAY;
 import static android.view.WindowManager.LayoutParams.TYPE_APPLICATION_STARTING;
-import static android.view.WindowManager.LayoutParams.TYPE_BASE_APPLICATION;
 import static android.view.WindowManager.LayoutParams.TYPE_BOOT_PROGRESS;
 import static android.view.WindowManager.LayoutParams.TYPE_DISPLAY_OVERLAY;
 import static android.view.WindowManager.LayoutParams.TYPE_DOCK_DIVIDER;
@@ -106,19 +67,13 @@
 import static android.view.WindowManager.LayoutParams.TYPE_PRIORITY_PHONE;
 import static android.view.WindowManager.LayoutParams.TYPE_PRIVATE_PRESENTATION;
 import static android.view.WindowManager.LayoutParams.TYPE_QS_DIALOG;
-import static android.view.WindowManager.LayoutParams.TYPE_SCREENSHOT;
 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;
 import static android.view.WindowManager.LayoutParams.TYPE_STATUS_BAR_PANEL;
 import static android.view.WindowManager.LayoutParams.TYPE_STATUS_BAR_SUB_PANEL;
-import static android.view.WindowManager.LayoutParams.TYPE_SYSTEM_ALERT;
 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_SYSTEM_OVERLAY;
 import static android.view.WindowManager.LayoutParams.TYPE_TOAST;
 import static android.view.WindowManager.LayoutParams.TYPE_VOICE_INTERACTION;
-import static android.view.WindowManager.LayoutParams.TYPE_VOICE_INTERACTION_STARTING;
 import static android.view.WindowManager.LayoutParams.TYPE_VOLUME_OVERLAY;
 import static android.view.WindowManager.LayoutParams.TYPE_WALLPAPER;
 import static android.view.WindowManager.LayoutParams.isSystemAlertWindowType;
@@ -132,25 +87,15 @@
 import static com.android.server.policy.WindowManagerPolicy.WindowManagerFuncs.CAMERA_LENS_UNCOVERED;
 import static com.android.server.policy.WindowManagerPolicy.WindowManagerFuncs.LID_CLOSED;
 import static com.android.server.policy.WindowManagerPolicy.WindowManagerFuncs.LID_OPEN;
-import static com.android.server.wm.WindowManagerPolicyProto.FOCUSED_APP_TOKEN;
-import static com.android.server.wm.WindowManagerPolicyProto.FOCUSED_WINDOW;
-import static com.android.server.wm.WindowManagerPolicyProto.FORCE_STATUS_BAR;
-import static com.android.server.wm.WindowManagerPolicyProto.FORCE_STATUS_BAR_FROM_KEYGUARD;
 import static com.android.server.wm.WindowManagerPolicyProto.KEYGUARD_DELEGATE;
 import static com.android.server.wm.WindowManagerPolicyProto.KEYGUARD_DRAW_COMPLETE;
 import static com.android.server.wm.WindowManagerPolicyProto.KEYGUARD_OCCLUDED;
 import static com.android.server.wm.WindowManagerPolicyProto.KEYGUARD_OCCLUDED_CHANGED;
 import static com.android.server.wm.WindowManagerPolicyProto.KEYGUARD_OCCLUDED_PENDING;
-import static com.android.server.wm.WindowManagerPolicyProto.LAST_SYSTEM_UI_FLAGS;
-import static com.android.server.wm.WindowManagerPolicyProto.NAVIGATION_BAR;
 import static com.android.server.wm.WindowManagerPolicyProto.ORIENTATION;
-import static com.android.server.wm.WindowManagerPolicyProto.ORIENTATION_LISTENER;
 import static com.android.server.wm.WindowManagerPolicyProto.ROTATION;
 import static com.android.server.wm.WindowManagerPolicyProto.ROTATION_MODE;
 import static com.android.server.wm.WindowManagerPolicyProto.SCREEN_ON_FULLY;
-import static com.android.server.wm.WindowManagerPolicyProto.STATUS_BAR;
-import static com.android.server.wm.WindowManagerPolicyProto.TOP_FULLSCREEN_OPAQUE_OR_DIMMING_WINDOW;
-import static com.android.server.wm.WindowManagerPolicyProto.TOP_FULLSCREEN_OPAQUE_WINDOW;
 import static com.android.server.wm.WindowManagerPolicyProto.WINDOW_MANAGER_DRAW_COMPLETE;
 
 import android.annotation.Nullable;
@@ -158,12 +103,10 @@
 import android.app.ActivityManagerInternal;
 import android.app.ActivityOptions;
 import android.app.ActivityTaskManager;
-import android.app.ActivityThread;
 import android.app.AppOpsManager;
 import android.app.IUiModeManager;
 import android.app.ProgressDialog;
 import android.app.SearchManager;
-import android.app.StatusBarManager;
 import android.app.UiModeManager;
 import android.content.ActivityNotFoundException;
 import android.content.BroadcastReceiver;
@@ -181,15 +124,12 @@
 import android.content.res.TypedArray;
 import android.database.ContentObserver;
 import android.graphics.PixelFormat;
-import android.graphics.Rect;
 import android.graphics.drawable.Drawable;
 import android.hardware.display.DisplayManager;
 import android.hardware.hdmi.HdmiControlManager;
 import android.hardware.hdmi.HdmiPlaybackClient;
 import android.hardware.hdmi.HdmiPlaybackClient.OneTouchPlayCallback;
-import android.hardware.input.InputManager;
 import android.hardware.input.InputManagerInternal;
-import android.hardware.power.V1_0.PowerHint;
 import android.media.AudioAttributes;
 import android.media.AudioManager;
 import android.media.AudioManagerInternal;
@@ -202,7 +142,6 @@
 import android.os.Handler;
 import android.os.IBinder;
 import android.os.IDeviceIdleController;
-import android.os.Looper;
 import android.os.Message;
 import android.os.PowerManager;
 import android.os.PowerManagerInternal;
@@ -224,7 +163,6 @@
 import android.service.vr.IPersistentVrStateCallbacks;
 import android.speech.RecognizerIntent;
 import android.telecom.TelecomManager;
-import android.util.ArraySet;
 import android.util.EventLog;
 import android.util.Log;
 import android.util.LongSparseArray;
@@ -234,21 +172,13 @@
 import android.util.SparseArray;
 import android.util.proto.ProtoOutputStream;
 import android.view.Display;
-import android.view.DisplayCutout;
-import android.view.Gravity;
 import android.view.HapticFeedbackConstants;
-import android.view.IApplicationToken;
 import android.view.IWindowManager;
-import android.view.InputChannel;
 import android.view.InputDevice;
-import android.view.InputEvent;
-import android.view.InputEventReceiver;
 import android.view.KeyCharacterMap;
 import android.view.KeyCharacterMap.FallbackAction;
 import android.view.KeyEvent;
 import android.view.MotionEvent;
-import android.view.PointerIcon;
-import android.view.Surface;
 import android.view.View;
 import android.view.ViewConfiguration;
 import android.view.WindowManager;
@@ -263,8 +193,6 @@
 
 import com.android.internal.R;
 import com.android.internal.accessibility.AccessibilityShortcutController;
-import com.android.internal.annotations.GuardedBy;
-import com.android.internal.annotations.VisibleForTesting;
 import com.android.internal.logging.MetricsLogger;
 import com.android.internal.logging.nano.MetricsProto;
 import com.android.internal.policy.IKeyguardDismissCallback;
@@ -272,7 +200,6 @@
 import com.android.internal.policy.PhoneWindow;
 import com.android.internal.statusbar.IStatusBarService;
 import com.android.internal.util.ArrayUtils;
-import com.android.internal.util.ScreenShapeHelper;
 import com.android.internal.util.ScreenshotHelper;
 import com.android.internal.widget.PointerLocationView;
 import com.android.server.ExtconStateObserver;
@@ -289,19 +216,17 @@
 import com.android.server.wm.ActivityTaskManagerInternal;
 import com.android.server.wm.ActivityTaskManagerInternal.SleepToken;
 import com.android.server.wm.AppTransition;
-import com.android.server.wm.DisplayFrames;
 import com.android.server.wm.DisplayPolicy;
 import com.android.server.wm.DisplayRotation;
-import com.android.server.wm.WindowFrames;
 import com.android.server.wm.WindowManagerInternal;
 import com.android.server.wm.WindowManagerInternal.AppTransitionListener;
-import com.android.server.wm.utils.InsetUtils;
 
 import java.io.File;
 import java.io.FileNotFoundException;
 import java.io.FileReader;
 import java.io.IOException;
 import java.io.PrintWriter;
+import java.util.HashSet;
 import java.util.List;
 
 /**
@@ -313,11 +238,9 @@
  */
 public class PhoneWindowManager implements WindowManagerPolicy {
     static final String TAG = "WindowManager";
-    static final boolean DEBUG = false;
     static final boolean localLOGV = false;
     static final boolean DEBUG_INPUT = false;
     static final boolean DEBUG_KEYGUARD = false;
-    static final boolean DEBUG_LAYOUT = false;
     static final boolean DEBUG_SPLASH_SCREEN = false;
     static final boolean DEBUG_WAKEUP = false;
     static final boolean SHOW_SPLASH_SCREENS = true;
@@ -329,8 +252,6 @@
     // Whether to allow devices placed in vr headset viewers to have an alternative Home intent.
     static final boolean ENABLE_VR_HEADSET_HOME_CAPTURE = true;
 
-    static final boolean ALTERNATE_CAR_MODE_NAV_SIZE = false;
-
     static final int SHORT_PRESS_POWER_NOTHING = 0;
     static final int SHORT_PRESS_POWER_GO_TO_SLEEP = 1;
     static final int SHORT_PRESS_POWER_REALLY_GO_TO_SLEEP = 2;
@@ -372,13 +293,6 @@
 
     static final int PENDING_KEY_NULL = -1;
 
-    // Controls navigation bar opacity depending on which workspace stacks are currently
-    // visible.
-    // Nav bar is always opaque when either the freeform stack or docked stack is visible.
-    static final int NAV_BAR_OPAQUE_WHEN_FREEFORM_OR_DOCKED = 0;
-    // Nav bar is always translucent when the freeform stack is visible, otherwise always opaque.
-    static final int NAV_BAR_TRANSLUCENT_WHEN_FREEFORM_OPAQUE_OTHERWISE = 1;
-
     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";
@@ -386,33 +300,11 @@
     static public final String SYSTEM_DIALOG_REASON_ASSIST = "assist";
     static public final String SYSTEM_DIALOG_REASON_SCREENSHOT = "screenshot";
 
-    /**
-     * These are the system UI flags that, when changing, can cause the layout
-     * of the screen to change.
-     */
-    static final int SYSTEM_UI_CHANGING_LAYOUT =
-              View.SYSTEM_UI_FLAG_HIDE_NAVIGATION
-            | View.SYSTEM_UI_FLAG_FULLSCREEN
-            | View.STATUS_BAR_TRANSLUCENT
-            | View.NAVIGATION_BAR_TRANSLUCENT
-            | View.STATUS_BAR_TRANSPARENT
-            | View.NAVIGATION_BAR_TRANSPARENT;
-
     private static final AudioAttributes VIBRATION_ATTRIBUTES = new AudioAttributes.Builder()
             .setContentType(AudioAttributes.CONTENT_TYPE_SONIFICATION)
             .setUsage(AudioAttributes.USAGE_ASSISTANCE_SONIFICATION)
             .build();
 
-    // The panic gesture may become active only after the keyguard is dismissed and the immersive
-    // app shows again. If that doesn't happen for 30s we drop the gesture.
-    private static final long PANIC_GESTURE_EXPIRATION = 30000;
-
-    private static final String SYSUI_PACKAGE = "com.android.systemui";
-    private static final String SYSUI_SCREENSHOT_SERVICE =
-            "com.android.systemui.screenshot.TakeScreenshotService";
-    private static final String SYSUI_SCREENSHOT_ERROR_RECEIVER =
-            "com.android.systemui.screenshot.ScreenshotServiceErrorReceiver";
-
     /**
      * Keyguard stuff
      */
@@ -501,16 +393,7 @@
     private AccessibilityShortcutController mAccessibilityShortcutController;
 
     boolean mSafeMode;
-    private final ArraySet<WindowState> mScreenDecorWindows = new ArraySet<>();
-    WindowState mStatusBar = null;
-    private final int[] mStatusBarHeightForRotation = new int[4];
-    WindowState mNavigationBar = null;
-    @NavigationBarPosition
-    int mNavigationBarPosition = NAV_BAR_BOTTOM;
-    int[] mNavigationBarHeightForRotationDefault = new int[4];
-    int[] mNavigationBarWidthForRotationDefault = new int[4];
-    int[] mNavigationBarHeightForRotationInCarMode = new int[4];
-    int[] mNavigationBarWidthForRotationInCarMode = new int[4];
+    private WindowState mKeyguardCandidate = null;
 
     private LongSparseArray<IShortcutService> mShortcutKeyServices = new LongSparseArray<>();
 
@@ -591,7 +474,6 @@
     int mShortPressOnSleepBehavior;
     int mShortPressOnWindowBehavior;
     boolean mHasSoftInput = false;
-    boolean mTranslucentDecorEnabled = true;
     boolean mUseTvRouting;
     int mVeryLongPressTimeout;
     boolean mAllowStartActivityForLongPressOnPowerDuringSetup;
@@ -600,74 +482,12 @@
     private boolean mHandleVolumeKeysInWM;
 
     int mPointerLocationMode = 0; // guarded by mLock
-
-    // The windows we were told about in focusChanged.
-    WindowState mFocusedWindow;
-    WindowState mLastFocusedWindow;
-
-    IApplicationToken mFocusedApp;
-
     PointerLocationView mPointerLocationView;
 
-    // During layout, the layer at which the doc window is placed.
-    int mDockLayer;
-    // During layout, this is the layer of the status bar.
-    int mStatusBarLayer;
-    int mLastSystemUiFlags;
-    // Bits that we are in the process of clearing, so we want to prevent
-    // them from being set by applications until everything has been updated
-    // to have them clear.
-    int mResettingSystemUiFlags = 0;
-    // Bits that we are currently always keeping cleared.
-    int mForceClearedSystemUiFlags = 0;
-    int mLastFullscreenStackSysUiFlags;
-    int mLastDockedStackSysUiFlags;
-    final Rect mNonDockedStackBounds = new Rect();
-    final Rect mDockedStackBounds = new Rect();
-    final Rect mLastNonDockedStackBounds = new Rect();
-    final Rect mLastDockedStackBounds = new Rect();
-
-    // What we last reported to system UI about whether the compatibility
-    // menu needs to be displayed.
-    boolean mLastFocusNeedsMenu = false;
-    // If nonzero, a panic gesture was performed at that time in uptime millis and is still pending.
-    private long mPendingPanicGestureUptime;
-
-    InputConsumer mInputConsumer = null;
-
-    private static final Rect sTmpDisplayCutoutSafeExceptMaybeBarsRect = new Rect();
-    private static final Rect sTmpRect = new Rect();
-    private static final Rect sTmpDockedFrame = new Rect();
-    private static final Rect sTmpNavFrame = new Rect();
-    private static final Rect sTmpLastParentFrame = new Rect();
-
-    WindowState mTopFullscreenOpaqueWindowState;
-    WindowState mTopFullscreenOpaqueOrDimmingWindowState;
-    WindowState mTopDockedOpaqueWindowState;
-    WindowState mTopDockedOpaqueOrDimmingWindowState;
-    boolean mTopIsFullscreen;
-    boolean mForceStatusBar;
-    boolean mForceStatusBarFromKeyguard;
-    private boolean mForceStatusBarTransparent;
-    int mNavBarOpacityMode = NAV_BAR_OPAQUE_WHEN_FREEFORM_OR_DOCKED;
-    boolean mForcingShowNavBar;
-    int mForcingShowNavBarLayer;
-
     private boolean mPendingKeyguardOccluded;
     private boolean mKeyguardOccludedChanged;
     private boolean mNotifyUserActivity;
 
-    boolean mShowingDream;
-    private boolean mLastShowingDream;
-    boolean mDreamingLockscreen;
-    boolean mDreamingSleepTokenNeeded;
-    private boolean mWindowSleepTokenNeeded;
-    private boolean mLastWindowSleepTokenNeeded;
-
-    @GuardedBy("mHandler")
-    private SleepToken mWindowSleepToken;
-
-    SleepToken mDreamingSleepToken;
     SleepToken mScreenOffSleepToken;
     volatile boolean mKeyguardOccluded;
     Intent mHomeIntent;
@@ -680,10 +500,9 @@
     boolean mPendingCapsLockToggle;
     int mMetaState;
     int mInitialMetaState;
-    boolean mForceShowSystemBars;
 
     // support for activating the lock screen while the screen is on
-    boolean mAllowLockscreenWhenOn;
+    private HashSet<Integer> mAllowLockscreenWhenOnDisplays = new HashSet<>();
     int mLockScreenTimeout;
     boolean mLockScreenTimerActive;
 
@@ -704,7 +523,6 @@
     Display mDefaultDisplay;
     DisplayRotation mDefaultDisplayRotation;
     DisplayPolicy mDefaultDisplayPolicy;
-    WindowOrientationListener mDefaultOrientationListener;
 
     // What we do when the user long presses on home
     private int mLongPressOnHomeBehavior;
@@ -781,10 +599,6 @@
 
     private boolean mAodShowing;
 
-    // EXPERIMENT TODO(b/113952590): Remove once experiment in bug is completed
-    private NavigationBarExperiments mExperiments = new NavigationBarExperiments();
-    // EXPERIMENT END
-
     private static final int MSG_ENABLE_POINTER_LOCATION = 1;
     private static final int MSG_DISABLE_POINTER_LOCATION = 2;
     private static final int MSG_DISPATCH_MEDIA_KEY_WITH_WAKE_LOCK = 3;
@@ -798,25 +612,19 @@
     private static final int MSG_LAUNCH_VOICE_ASSIST_WITH_WAKE_LOCK = 12;
     private static final int MSG_POWER_DELAYED_PRESS = 13;
     private static final int MSG_POWER_LONG_PRESS = 14;
-    private static final int MSG_UPDATE_DREAMING_SLEEP_TOKEN = 15;
-    private static final int MSG_REQUEST_TRANSIENT_BARS = 16;
-    private static final int MSG_SHOW_PICTURE_IN_PICTURE_MENU = 17;
-    private static final int MSG_BACK_LONG_PRESS = 18;
-    private static final int MSG_DISPOSE_INPUT_CONSUMER = 19;
-    private static final int MSG_ACCESSIBILITY_SHORTCUT = 20;
-    private static final int MSG_BUGREPORT_TV = 21;
-    private static final int MSG_ACCESSIBILITY_TV = 22;
-    private static final int MSG_DISPATCH_BACK_KEY_TO_AUTOFILL = 23;
-    private static final int MSG_SYSTEM_KEY_PRESS = 24;
-    private static final int MSG_HANDLE_ALL_APPS = 25;
-    private static final int MSG_LAUNCH_ASSIST = 26;
-    private static final int MSG_LAUNCH_ASSIST_LONG_PRESS = 27;
-    private static final int MSG_POWER_VERY_LONG_PRESS = 28;
-    private static final int MSG_NOTIFY_USER_ACTIVITY = 29;
-    private static final int MSG_RINGER_TOGGLE_CHORD = 30;
-
-    private static final int MSG_REQUEST_TRANSIENT_BARS_ARG_STATUS = 0;
-    private static final int MSG_REQUEST_TRANSIENT_BARS_ARG_NAVIGATION = 1;
+    private static final int MSG_SHOW_PICTURE_IN_PICTURE_MENU = 15;
+    private static final int MSG_BACK_LONG_PRESS = 16;
+    private static final int MSG_ACCESSIBILITY_SHORTCUT = 17;
+    private static final int MSG_BUGREPORT_TV = 18;
+    private static final int MSG_ACCESSIBILITY_TV = 19;
+    private static final int MSG_DISPATCH_BACK_KEY_TO_AUTOFILL = 20;
+    private static final int MSG_SYSTEM_KEY_PRESS = 21;
+    private static final int MSG_HANDLE_ALL_APPS = 22;
+    private static final int MSG_LAUNCH_ASSIST = 23;
+    private static final int MSG_LAUNCH_ASSIST_LONG_PRESS = 24;
+    private static final int MSG_POWER_VERY_LONG_PRESS = 25;
+    private static final int MSG_NOTIFY_USER_ACTIVITY = 26;
+    private static final int MSG_RINGER_TOGGLE_CHORD = 27;
 
     private class PolicyHandler extends Handler {
         @Override
@@ -876,25 +684,12 @@
                 case MSG_POWER_VERY_LONG_PRESS:
                     powerVeryLongPress();
                     break;
-                case MSG_UPDATE_DREAMING_SLEEP_TOKEN:
-                    updateDreamingSleepToken(msg.arg1 != 0);
-                    break;
-                case MSG_REQUEST_TRANSIENT_BARS:
-                    WindowState targetBar = (msg.arg1 == MSG_REQUEST_TRANSIENT_BARS_ARG_STATUS) ?
-                            mStatusBar : mNavigationBar;
-                    if (targetBar != null) {
-                        requestTransientBars(targetBar);
-                    }
-                    break;
                 case MSG_SHOW_PICTURE_IN_PICTURE_MENU:
                     showPictureInPictureMenuInternal();
                     break;
                 case MSG_BACK_LONG_PRESS:
                     backLongPress();
                     break;
-                case MSG_DISPOSE_INPUT_CONSUMER:
-                    disposeInputConsumer((InputConsumer) msg.obj);
-                    break;
                 case MSG_ACCESSIBILITY_SHORTCUT:
                     accessibilityShortcutActivated();
                     break;
@@ -966,14 +761,8 @@
                     Settings.Secure.DEFAULT_INPUT_METHOD), false, this,
                     UserHandle.USER_ALL);
             resolver.registerContentObserver(Settings.Secure.getUriFor(
-                    Settings.Secure.IMMERSIVE_MODE_CONFIRMATIONS), false, this,
-                    UserHandle.USER_ALL);
-            resolver.registerContentObserver(Settings.Secure.getUriFor(
                     Settings.Secure.VOLUME_HUSH_GESTURE), false, this,
                     UserHandle.USER_ALL);
-            resolver.registerContentObserver(Settings.Global.getUriFor(
-                    Settings.Global.POLICY_CONTROL), false, this,
-                    UserHandle.USER_ALL);
             resolver.registerContentObserver(Settings.Secure.getUriFor(
                     Settings.Secure.SYSTEM_NAVIGATION_KEYS_ENABLED), false, this,
                     UserHandle.USER_ALL);
@@ -1012,45 +801,6 @@
         }
     };
 
-    private final StatusBarController mStatusBarController = new StatusBarController();
-
-    private final BarController mNavigationBarController = new BarController("NavigationBar",
-            View.NAVIGATION_BAR_TRANSIENT,
-            View.NAVIGATION_BAR_UNHIDE,
-            View.NAVIGATION_BAR_TRANSLUCENT,
-            StatusBarManager.WINDOW_NAVIGATION_BAR,
-            FLAG_TRANSLUCENT_NAVIGATION,
-            View.NAVIGATION_BAR_TRANSPARENT);
-
-    private final BarController.OnBarVisibilityChangedListener mNavBarVisibilityListener =
-            new BarController.OnBarVisibilityChangedListener() {
-        @Override
-        public void onBarVisibilityChanged(boolean visible) {
-            mAccessibilityManager.notifyAccessibilityButtonVisibilityChanged(visible);
-        }
-    };
-
-    private final Runnable mAcquireSleepTokenRunnable = () -> {
-        if (mWindowSleepToken != null) {
-            return;
-        }
-        mWindowSleepToken = mActivityTaskManagerInternal.acquireSleepToken("WindowSleepToken",
-                DEFAULT_DISPLAY);
-    };
-
-    private final Runnable mReleaseSleepTokenRunnable = () -> {
-        if (mWindowSleepToken == null) {
-            return;
-        }
-        mWindowSleepToken.release();
-        mWindowSleepToken = null;
-    };
-
-    private ImmersiveModeConfirmation mImmersiveModeConfirmation;
-
-    @VisibleForTesting
-    SystemGesturesPointerEventListener mSystemGestures;
-
     private void handleRingerChordGesture() {
         if (mRingerToggleChord == VOLUME_HUSH_OFF) {
             return;
@@ -1150,14 +900,7 @@
             mHandler.removeMessages(MSG_POWER_DELAYED_PRESS);
         }
 
-        // Detect user pressing the power button in panic when an application has
-        // taken over the whole screen.
-        boolean panic = mImmersiveModeConfirmation.onPowerKeyDown(interactive,
-                SystemClock.elapsedRealtime(), isImmersiveMode(mLastSystemUiFlags),
-                isNavBarEmpty(mLastSystemUiFlags));
-        if (panic) {
-            mHandler.post(mHiddenNavPanic);
-        }
+        mWindowManagerFuncs.onPowerKeyDown(interactive);
 
         // Abort possibly stuck animations.
         mHandler.post(mWindowManagerFuncs::triggerAnimationFailsafe);
@@ -1500,12 +1243,6 @@
         mAccessibilityShortcutController.performAccessibilityShortcut();
     }
 
-    private void disposeInputConsumer(InputConsumer inputConsumer) {
-        if (inputConsumer != null) {
-            inputConsumer.dismiss();
-        }
-    }
-
     private void sleepPress() {
         if (mShortPressOnSleepBehavior == SHORT_PRESS_SLEEP_GO_TO_SLEEP_AND_GO_HOME) {
             launchHomeFromHotKey(DEFAULT_DISPLAY, false /* awakenDreams */,
@@ -1643,9 +1380,7 @@
 
         @Override
         public void run() {
-            mScreenshotHelper.takeScreenshot(mScreenshotType,
-                    mStatusBar != null && mStatusBar.isVisibleLw(),
-                    mNavigationBar != null && mNavigationBar.isVisibleLw(), mHandler);
+            mDefaultDisplayPolicy.takeScreenshot(mScreenshotType);
         }
     }
 
@@ -1673,7 +1408,8 @@
                 mContext.getContentResolver(), Settings.Global.DEVICE_PROVISIONED, 0) != 0;
     }
 
-    boolean isUserSetupComplete() {
+    @Override
+    public boolean isUserSetupComplete() {
         boolean isSetupComplete = Settings.Secure.getIntForUser(mContext.getContentResolver(),
                 Settings.Secure.USER_SETUP_COMPLETE, 0, UserHandle.USER_CURRENT) != 0;
         if (mHasFeatureLeanback) {
@@ -1931,7 +1667,6 @@
         mDefaultDisplay = displayContentInfo.getDisplay();
         mDefaultDisplayRotation = displayContentInfo.getDisplayRotation();
         mDefaultDisplayPolicy = mDefaultDisplayRotation.getDisplayPolicy();
-        mDefaultOrientationListener = mDefaultDisplayRotation.getOrientationListener();
     }
 
     /** {@inheritDoc} */
@@ -2028,8 +1763,6 @@
                 com.android.internal.R.bool.config_lidControlsScreenLock);
         mLidControlsSleep = mContext.getResources().getBoolean(
                 com.android.internal.R.bool.config_lidControlsSleep);
-        mTranslucentDecorEnabled = mContext.getResources().getBoolean(
-                com.android.internal.R.bool.config_enableTranslucentDecor);
 
         mAllowTheaterModeWakeFromKey = mContext.getResources().getBoolean(
                 com.android.internal.R.bool.config_allowTheaterModeWakeFromKey);
@@ -2107,76 +1840,6 @@
         filter = new IntentFilter(Intent.ACTION_USER_SWITCHED);
         context.registerReceiver(mMultiuserReceiver, filter);
 
-        // monitor for system gestures
-        // TODO(multi-display): Needs to be display specific.
-        mSystemGestures = new SystemGesturesPointerEventListener(context,
-                new SystemGesturesPointerEventListener.Callbacks() {
-                    @Override
-                    public void onSwipeFromTop() {
-                        if (mStatusBar != null) {
-                            requestTransientBars(mStatusBar);
-                        }
-                    }
-                    @Override
-                    public void onSwipeFromBottom() {
-                        if (mNavigationBar != null && mNavigationBarPosition == NAV_BAR_BOTTOM) {
-                            requestTransientBars(mNavigationBar);
-                        }
-                    }
-                    @Override
-                    public void onSwipeFromRight() {
-                        if (mNavigationBar != null && mNavigationBarPosition == NAV_BAR_RIGHT) {
-                            requestTransientBars(mNavigationBar);
-                        }
-                    }
-                    @Override
-                    public void onSwipeFromLeft() {
-                        if (mNavigationBar != null && mNavigationBarPosition == NAV_BAR_LEFT) {
-                            requestTransientBars(mNavigationBar);
-                        }
-                    }
-                    @Override
-                    public void onFling(int duration) {
-                        if (mPowerManagerInternal != null) {
-                            mPowerManagerInternal.powerHint(
-                                    PowerHint.INTERACTION, duration);
-                        }
-                    }
-                    @Override
-                    public void onDebug() {
-                        // no-op
-                    }
-                    @Override
-                    public void onDown() {
-                        mDefaultOrientationListener.onTouchStart();
-                    }
-                    @Override
-                    public void onUpOrCancel() {
-                        mDefaultOrientationListener.onTouchEnd();
-                    }
-                    @Override
-                    public void onMouseHoverAtTop() {
-                        mHandler.removeMessages(MSG_REQUEST_TRANSIENT_BARS);
-                        Message msg = mHandler.obtainMessage(MSG_REQUEST_TRANSIENT_BARS);
-                        msg.arg1 = MSG_REQUEST_TRANSIENT_BARS_ARG_STATUS;
-                        mHandler.sendMessageDelayed(msg, 500);
-                    }
-                    @Override
-                    public void onMouseHoverAtBottom() {
-                        mHandler.removeMessages(MSG_REQUEST_TRANSIENT_BARS);
-                        Message msg = mHandler.obtainMessage(MSG_REQUEST_TRANSIENT_BARS);
-                        msg.arg1 = MSG_REQUEST_TRANSIENT_BARS_ARG_NAVIGATION;
-                        mHandler.sendMessageDelayed(msg, 500);
-                    }
-                    @Override
-                    public void onMouseLeaveFromEdge() {
-                        mHandler.removeMessages(MSG_REQUEST_TRANSIENT_BARS);
-                    }
-                });
-        mImmersiveModeConfirmation = new ImmersiveModeConfirmation(mContext);
-        //TODO (b/111365687) : make system context per display.
-        mWindowManagerFuncs.registerPointerEventListener(mSystemGestures, DEFAULT_DISPLAY);
-
         mVibrator = (Vibrator)context.getSystemService(Context.VIBRATOR_SERVICE);
         mLongPressVibePattern = getLongIntArray(mContext.getResources(),
                 com.android.internal.R.array.config_longPressVibePattern);
@@ -2199,8 +1862,6 @@
             finishedGoingToSleep(WindowManagerPolicy.OFF_BECAUSE_OF_USER);
         }
 
-        mWindowManagerInternal.registerAppTransitionListener(
-                mStatusBarController.getAppTransitionListener());
         mWindowManagerInternal.registerAppTransitionListener(new AppTransitionListener() {
             @Override
             public int onAppTransitionStartingLocked(int transit, IBinder openToken,
@@ -2255,16 +1916,6 @@
         if (mContext.getPackageManager().hasSystemFeature(FEATURE_PICTURE_IN_PICTURE)) {
             mShortPressOnWindowBehavior = SHORT_PRESS_WINDOW_PICTURE_IN_PICTURE;
         }
-
-        mNavBarOpacityMode = res.getInteger(
-                com.android.internal.R.integer.config_navBarOpacityMode);
-    }
-
-    /**
-     * @return whether the navigation bar can be hidden, e.g. the device has a navigation bar
-     */
-    private boolean canHideNavigationBar() {
-        return mDefaultDisplayPolicy.hasNavigationBar();
     }
 
     public void updateSettings() {
@@ -2322,12 +1973,6 @@
                 mHasSoftInput = hasSoftInput;
                 updateRotation = true;
             }
-            if (mImmersiveModeConfirmation != null) {
-                mImmersiveModeConfirmation.loadSetting(mCurrentUserId);
-            }
-        }
-        synchronized (mWindowManagerFuncs.getWindowManagerLock()) {
-            PolicyControl.reloadFromSetting(mContext);
         }
         if (updateRotation) {
             updateRotation(true);
@@ -2536,84 +2181,6 @@
         return mContext.checkCallingOrSelfPermission(INTERNAL_SYSTEM_WINDOW) != PERMISSION_GRANTED;
     }
 
-    @Override
-    public void adjustWindowParamsLw(WindowState win, WindowManager.LayoutParams attrs,
-            boolean hasStatusBarServicePermission) {
-
-        final boolean isScreenDecor = (attrs.privateFlags & PRIVATE_FLAG_IS_SCREEN_DECOR) != 0;
-        if (mScreenDecorWindows.contains(win)) {
-            if (!isScreenDecor) {
-                // No longer has the flag set, so remove from the set.
-                mScreenDecorWindows.remove(win);
-            }
-        } else if (isScreenDecor && hasStatusBarServicePermission) {
-            mScreenDecorWindows.add(win);
-        }
-
-        switch (attrs.type) {
-            case TYPE_SYSTEM_OVERLAY:
-            case TYPE_SECURE_SYSTEM_OVERLAY:
-                // These types of windows can't receive input events.
-                attrs.flags |= WindowManager.LayoutParams.FLAG_NOT_FOCUSABLE
-                        | WindowManager.LayoutParams.FLAG_NOT_TOUCHABLE;
-                attrs.flags &= ~WindowManager.LayoutParams.FLAG_WATCH_OUTSIDE_TOUCH;
-                break;
-            case TYPE_DREAM:
-            case TYPE_WALLPAPER:
-                // Dreams and wallpapers don't have an app window token and can thus not be
-                // letterboxed. Hence always let them extend under the cutout.
-                attrs.layoutInDisplayCutoutMode = LAYOUT_IN_DISPLAY_CUTOUT_MODE_ALWAYS;
-                break;
-            case TYPE_STATUS_BAR:
-
-                // If the Keyguard is in a hidden state (occluded by another window), we force to
-                // remove the wallpaper and keyguard flag so that any change in-flight after setting
-                // the keyguard as occluded wouldn't set these flags again.
-                // See {@link #processKeyguardSetHiddenResultLw}.
-                if (mKeyguardOccluded) {
-                    attrs.flags &= ~WindowManager.LayoutParams.FLAG_SHOW_WALLPAPER;
-                    attrs.privateFlags &= ~WindowManager.LayoutParams.PRIVATE_FLAG_KEYGUARD;
-                }
-                break;
-
-            case TYPE_SCREENSHOT:
-                attrs.flags |= WindowManager.LayoutParams.FLAG_NOT_FOCUSABLE;
-                break;
-
-            case TYPE_TOAST:
-                // While apps should use the dedicated toast APIs to add such windows
-                // it possible legacy apps to add the window directly. Therefore, we
-                // make windows added directly by the app behave as a toast as much
-                // as possible in terms of timeout and animation.
-                if (attrs.hideTimeoutMilliseconds < 0
-                        || attrs.hideTimeoutMilliseconds > TOAST_WINDOW_TIMEOUT) {
-                    attrs.hideTimeoutMilliseconds = TOAST_WINDOW_TIMEOUT;
-                }
-                attrs.windowAnimations = com.android.internal.R.style.Animation_Toast;
-                break;
-        }
-
-        if (attrs.type != TYPE_STATUS_BAR) {
-            // The status bar is the only window allowed to exhibit keyguard behavior.
-            attrs.privateFlags &= ~WindowManager.LayoutParams.PRIVATE_FLAG_KEYGUARD;
-        }
-    }
-
-    private int getImpliedSysUiFlagsForLayout(LayoutParams attrs) {
-        int impliedFlags = 0;
-        if ((attrs.flags & FLAG_DRAWS_SYSTEM_BAR_BACKGROUNDS) != 0) {
-            impliedFlags |= View.SYSTEM_UI_FLAG_LAYOUT_HIDE_NAVIGATION;
-        }
-        final boolean forceWindowDrawsStatusBarBackground =
-                (attrs.privateFlags & PRIVATE_FLAG_FORCE_DRAW_STATUS_BAR_BACKGROUND) != 0;
-        if ((attrs.flags & FLAG_DRAWS_SYSTEM_BAR_BACKGROUNDS) != 0
-                || forceWindowDrawsStatusBarBackground
-                        && attrs.height == MATCH_PARENT && attrs.width == MATCH_PARENT) {
-            impliedFlags |= View.SYSTEM_UI_FLAG_LAYOUT_FULLSCREEN;
-        }
-        return impliedFlags;
-    }
-
     void readLidState() {
         mDefaultDisplayPolicy.setLidState(mWindowManagerFuncs.getLidState());
     }
@@ -2660,161 +2227,10 @@
     }
 
     @Override
-    public void onOverlayChangedLw(DisplayContentInfo displayContentInfo) {
-        onConfigurationChanged(displayContentInfo);
-    }
-
-    @Override
-    public void onConfigurationChanged(DisplayContentInfo displayContentInfo) {
-        final DisplayRotation displayRotation = displayContentInfo.getDisplayRotation();
-        // TODO(multi-display): Define policy for secondary displays.
-        if (!displayRotation.isDefaultDisplay) {
-            return;
-        }
-
-        final Context uiContext = getSystemUiContext();
-        final Resources res = uiContext.getResources();
-        final int portraitRotation = displayRotation.getPortraitRotation();
-        final int upsideDownRotation = displayRotation.getUpsideDownRotation();
-        final int landscapeRotation = displayRotation.getLandscapeRotation();
-        final int seascapeRotation = displayRotation.getSeascapeRotation();
-
-        mStatusBarHeightForRotation[portraitRotation] =
-                mStatusBarHeightForRotation[upsideDownRotation] = res.getDimensionPixelSize(
-                                com.android.internal.R.dimen.status_bar_height_portrait);
-        mStatusBarHeightForRotation[landscapeRotation] =
-                mStatusBarHeightForRotation[seascapeRotation] = res.getDimensionPixelSize(
-                        com.android.internal.R.dimen.status_bar_height_landscape);
-
-        // Height of the navigation bar when presented horizontally at bottom
-        mNavigationBarHeightForRotationDefault[portraitRotation] =
-        mNavigationBarHeightForRotationDefault[upsideDownRotation] =
-                res.getDimensionPixelSize(com.android.internal.R.dimen.navigation_bar_height);
-        mNavigationBarHeightForRotationDefault[landscapeRotation] =
-        mNavigationBarHeightForRotationDefault[seascapeRotation] = res.getDimensionPixelSize(
-                com.android.internal.R.dimen.navigation_bar_height_landscape);
-
-        // Width of the navigation bar when presented vertically along one side
-        mNavigationBarWidthForRotationDefault[portraitRotation] =
-        mNavigationBarWidthForRotationDefault[upsideDownRotation] =
-        mNavigationBarWidthForRotationDefault[landscapeRotation] =
-        mNavigationBarWidthForRotationDefault[seascapeRotation] =
-                res.getDimensionPixelSize(com.android.internal.R.dimen.navigation_bar_width);
-
-        if (ALTERNATE_CAR_MODE_NAV_SIZE) {
-            // Height of the navigation bar when presented horizontally at bottom
-            mNavigationBarHeightForRotationInCarMode[portraitRotation] =
-            mNavigationBarHeightForRotationInCarMode[upsideDownRotation] =
-                    res.getDimensionPixelSize(
-                            com.android.internal.R.dimen.navigation_bar_height_car_mode);
-            mNavigationBarHeightForRotationInCarMode[landscapeRotation] =
-            mNavigationBarHeightForRotationInCarMode[seascapeRotation] = res.getDimensionPixelSize(
-                    com.android.internal.R.dimen.navigation_bar_height_landscape_car_mode);
-
-            // Width of the navigation bar when presented vertically along one side
-            mNavigationBarWidthForRotationInCarMode[portraitRotation] =
-            mNavigationBarWidthForRotationInCarMode[upsideDownRotation] =
-            mNavigationBarWidthForRotationInCarMode[landscapeRotation] =
-            mNavigationBarWidthForRotationInCarMode[seascapeRotation] =
-                    res.getDimensionPixelSize(
-                            com.android.internal.R.dimen.navigation_bar_width_car_mode);
-        }
-
-        // EXPERIMENT TODO(b/113952590): Remove once experiment in bug is completed
-        mExperiments.onConfigurationChanged(uiContext);
-        // EXPERIMENT END
-    }
-
-    @VisibleForTesting
-    Context getSystemUiContext() {
-        return ActivityThread.currentActivityThread().getSystemUiContext();
-    }
-
-    @Override
     public int getMaxWallpaperLayer() {
         return getWindowLayerFromTypeLw(TYPE_STATUS_BAR);
     }
 
-    private int getNavigationBarWidth(int rotation, int uiMode) {
-        if (ALTERNATE_CAR_MODE_NAV_SIZE && (uiMode & UI_MODE_TYPE_MASK) == UI_MODE_TYPE_CAR) {
-            return mNavigationBarWidthForRotationInCarMode[rotation];
-        } else {
-            return mNavigationBarWidthForRotationDefault[rotation];
-        }
-    }
-
-    @Override
-    public int getNonDecorDisplayWidth(int fullWidth, int fullHeight, int rotation, int uiMode,
-            int displayId, DisplayCutout displayCutout) {
-        int width = fullWidth;
-        // TODO(multi-display): Support navigation bar on secondary displays.
-        if (displayId == DEFAULT_DISPLAY && mDefaultDisplayPolicy.hasNavigationBar()) {
-            // For a basic navigation bar, when we are in landscape mode we place
-            // the navigation bar to the side.
-            if (mDefaultDisplayPolicy.navigationBarCanMove() && fullWidth > fullHeight) {
-                width -= getNavigationBarWidth(rotation, uiMode);
-            }
-        }
-        if (displayCutout != null) {
-            width -= displayCutout.getSafeInsetLeft() + displayCutout.getSafeInsetRight();
-        }
-        return width;
-    }
-
-    private int getNavigationBarHeight(int rotation, int uiMode) {
-        if (ALTERNATE_CAR_MODE_NAV_SIZE && (uiMode & UI_MODE_TYPE_MASK) == UI_MODE_TYPE_CAR) {
-            return mNavigationBarHeightForRotationInCarMode[rotation];
-        } else {
-            return mNavigationBarHeightForRotationDefault[rotation];
-        }
-    }
-
-    @Override
-    public int getNonDecorDisplayHeight(int fullWidth, int fullHeight, int rotation, int uiMode,
-            int displayId, DisplayCutout displayCutout) {
-        int height = fullHeight;
-        // TODO(multi-display): Support navigation bar on secondary displays.
-        if (displayId == DEFAULT_DISPLAY && mDefaultDisplayPolicy.hasNavigationBar()) {
-            // For a basic navigation bar, when we are in portrait mode we place
-            // the navigation bar to the bottom.
-            if (!mDefaultDisplayPolicy.navigationBarCanMove() || fullWidth < fullHeight) {
-                height -= getNavigationBarHeight(rotation, uiMode);
-            }
-        }
-        if (displayCutout != null) {
-            height -= displayCutout.getSafeInsetTop() + displayCutout.getSafeInsetBottom();
-        }
-        return height;
-    }
-
-    @Override
-    public int getConfigDisplayWidth(int fullWidth, int fullHeight, int rotation, int uiMode,
-            int displayId, DisplayCutout displayCutout) {
-        return getNonDecorDisplayWidth(fullWidth, fullHeight, rotation, uiMode, displayId,
-                displayCutout);
-    }
-
-    @Override
-    public int getConfigDisplayHeight(int fullWidth, int fullHeight, int rotation, int uiMode,
-            int displayId, DisplayCutout displayCutout) {
-        // There is a separate status bar at the top of the display.  We don't count that as part
-        // of the fixed decor, since it can hide; however, for purposes of configurations,
-        // we do want to exclude it since applications can't generally use that part
-        // of the screen.
-        // TODO(multi-display): Support status bars on secondary displays.
-        if (displayId == DEFAULT_DISPLAY) {
-            int statusBarHeight = mStatusBarHeightForRotation[rotation];
-            if (displayCutout != null) {
-                // If there is a cutout, it may already have accounted for some part of the status
-                // bar height.
-                statusBarHeight = Math.max(0, statusBarHeight - displayCutout.getSafeInsetTop());
-            }
-            return getNonDecorDisplayHeight(fullWidth, fullHeight, rotation, uiMode, displayId,
-                    displayCutout) - statusBarHeight;
-        }
-        return fullHeight;
-    }
-
     @Override
     public boolean isKeyguardHostWindow(WindowManager.LayoutParams attrs) {
         return attrs.type == TYPE_STATUS_BAR;
@@ -3054,251 +2470,6 @@
         return context.createDisplayContext(targetDisplay);
     }
 
-    /**
-     * Preflight adding a window to the system.
-     *
-     * Currently enforces that three window types are singletons:
-     * <ul>
-     * <li>STATUS_BAR_TYPE</li>
-     * <li>KEYGUARD_TYPE</li>
-     * </ul>
-     *
-     * @param win The window to be added
-     * @param attrs Information about the window to be added
-     *
-     * @return If ok, WindowManagerImpl.ADD_OKAY.  If too many singletons,
-     * WindowManagerImpl.ADD_MULTIPLE_SINGLETON
-     */
-    @Override
-    public int prepareAddWindowLw(WindowState win, WindowManager.LayoutParams attrs) {
-
-        if ((attrs.privateFlags & PRIVATE_FLAG_IS_SCREEN_DECOR) != 0) {
-            mContext.enforceCallingOrSelfPermission(
-                    android.Manifest.permission.STATUS_BAR_SERVICE,
-                    "PhoneWindowManager");
-            mScreenDecorWindows.add(win);
-        }
-
-        switch (attrs.type) {
-            case TYPE_STATUS_BAR:
-                mContext.enforceCallingOrSelfPermission(
-                        android.Manifest.permission.STATUS_BAR_SERVICE,
-                        "PhoneWindowManager");
-                if (mStatusBar != null) {
-                    if (mStatusBar.isAlive()) {
-                        return WindowManagerGlobal.ADD_MULTIPLE_SINGLETON;
-                    }
-                }
-                mStatusBar = win;
-                mStatusBarController.setWindow(win);
-                setKeyguardOccludedLw(mKeyguardOccluded, true /* force */);
-                break;
-            case TYPE_NAVIGATION_BAR:
-                mContext.enforceCallingOrSelfPermission(
-                        android.Manifest.permission.STATUS_BAR_SERVICE,
-                        "PhoneWindowManager");
-                if (mNavigationBar != null) {
-                    if (mNavigationBar.isAlive()) {
-                        return WindowManagerGlobal.ADD_MULTIPLE_SINGLETON;
-                    }
-                }
-                mNavigationBar = win;
-                mNavigationBarController.setWindow(win);
-                mNavigationBarController.setOnBarVisibilityChangedListener(
-                        mNavBarVisibilityListener, true);
-                if (DEBUG_LAYOUT) Slog.i(TAG, "NAVIGATION BAR: " + mNavigationBar);
-                break;
-            case TYPE_NAVIGATION_BAR_PANEL:
-            case TYPE_STATUS_BAR_PANEL:
-            case TYPE_STATUS_BAR_SUB_PANEL:
-            case TYPE_VOICE_INTERACTION_STARTING:
-                mContext.enforceCallingOrSelfPermission(
-                        android.Manifest.permission.STATUS_BAR_SERVICE,
-                        "PhoneWindowManager");
-                break;
-        }
-        return ADD_OKAY;
-    }
-
-    /** {@inheritDoc} */
-    @Override
-    public void removeWindowLw(WindowState win) {
-        if (mStatusBar == win) {
-            mStatusBar = null;
-            mStatusBarController.setWindow(null);
-        } else if (mNavigationBar == win) {
-            mNavigationBar = null;
-            mNavigationBarController.setWindow(null);
-        }
-        if (mLastFocusedWindow == win) {
-            mLastFocusedWindow = null;
-        }
-        mScreenDecorWindows.remove(win);
-    }
-
-    static final boolean PRINT_ANIM = false;
-
-    /** {@inheritDoc} */
-    @Override
-    public int selectAnimationLw(WindowState win, int transit) {
-        if (PRINT_ANIM) Log.i(TAG, "selectAnimation in " + win
-              + ": transit=" + transit);
-        if (win == mStatusBar) {
-            final boolean isKeyguard = (win.getAttrs().privateFlags & PRIVATE_FLAG_KEYGUARD) != 0;
-            final boolean expanded = win.getAttrs().height == MATCH_PARENT
-                    && win.getAttrs().width == MATCH_PARENT;
-            if (isKeyguard || expanded) {
-                return -1;
-            }
-            if (transit == TRANSIT_EXIT
-                    || transit == TRANSIT_HIDE) {
-                return R.anim.dock_top_exit;
-            } else if (transit == TRANSIT_ENTER
-                    || transit == TRANSIT_SHOW) {
-                return R.anim.dock_top_enter;
-            }
-        } else if (win == mNavigationBar) {
-            if (win.getAttrs().windowAnimations != 0) {
-                return 0;
-            }
-            // This can be on either the bottom or the right or the left.
-            if (mNavigationBarPosition == NAV_BAR_BOTTOM) {
-                if (transit == TRANSIT_EXIT
-                        || transit == TRANSIT_HIDE) {
-                    if (isKeyguardShowingAndNotOccluded()) {
-                        return R.anim.dock_bottom_exit_keyguard;
-                    } else {
-                        return R.anim.dock_bottom_exit;
-                    }
-                } else if (transit == TRANSIT_ENTER
-                        || transit == TRANSIT_SHOW) {
-                    return R.anim.dock_bottom_enter;
-                }
-            } else if (mNavigationBarPosition == NAV_BAR_RIGHT) {
-                if (transit == TRANSIT_EXIT
-                        || transit == TRANSIT_HIDE) {
-                    return R.anim.dock_right_exit;
-                } else if (transit == TRANSIT_ENTER
-                        || transit == TRANSIT_SHOW) {
-                    return R.anim.dock_right_enter;
-                }
-            } else if (mNavigationBarPosition == NAV_BAR_LEFT) {
-                if (transit == TRANSIT_EXIT
-                        || transit == TRANSIT_HIDE) {
-                    return R.anim.dock_left_exit;
-                } else if (transit == TRANSIT_ENTER
-                        || transit == TRANSIT_SHOW) {
-                    return R.anim.dock_left_enter;
-                }
-            }
-        } else if (win.getAttrs().type == TYPE_DOCK_DIVIDER) {
-            return selectDockedDividerAnimationLw(win, transit);
-        }
-
-        if (transit == TRANSIT_PREVIEW_DONE) {
-            if (win.hasAppShownWindows()) {
-                if (PRINT_ANIM) Log.i(TAG, "**** STARTING EXIT");
-                return com.android.internal.R.anim.app_starting_exit;
-            }
-        } else if (win.getAttrs().type == TYPE_DREAM && mDreamingLockscreen
-                && transit == TRANSIT_ENTER) {
-            // Special case: we are animating in a dream, while the keyguard
-            // is shown.  We don't want an animation on the dream, because
-            // we need it shown immediately with the keyguard animating away
-            // to reveal it.
-            return -1;
-        }
-
-        return 0;
-    }
-
-    private int selectDockedDividerAnimationLw(WindowState win, int transit) {
-        int insets = mWindowManagerFuncs.getDockedDividerInsetsLw();
-
-        // If the divider is behind the navigation bar, don't animate.
-        final Rect frame = win.getFrameLw();
-        final boolean behindNavBar = mNavigationBar != null
-                && ((mNavigationBarPosition == NAV_BAR_BOTTOM
-                        && frame.top + insets >= mNavigationBar.getFrameLw().top)
-                || (mNavigationBarPosition == NAV_BAR_RIGHT
-                        && frame.left + insets >= mNavigationBar.getFrameLw().left)
-                || (mNavigationBarPosition == NAV_BAR_LEFT
-                        && frame.right - insets <= mNavigationBar.getFrameLw().right));
-        final boolean landscape = frame.height() > frame.width();
-        final boolean offscreenLandscape = landscape && (frame.right - insets <= 0
-                || frame.left + insets >= win.getDisplayFrameLw().right);
-        final boolean offscreenPortrait = !landscape && (frame.top - insets <= 0
-                || frame.bottom + insets >= win.getDisplayFrameLw().bottom);
-        final boolean offscreen = offscreenLandscape || offscreenPortrait;
-        if (behindNavBar || offscreen) {
-            return 0;
-        }
-        if (transit == TRANSIT_ENTER || transit == TRANSIT_SHOW) {
-            return R.anim.fade_in;
-        } else if (transit == TRANSIT_EXIT) {
-            return R.anim.fade_out;
-        } else {
-            return 0;
-        }
-    }
-
-    @Override
-    public void selectRotationAnimationLw(int anim[]) {
-        // If the screen is off or non-interactive, force a jumpcut.
-        final boolean forceJumpcut = !mDefaultDisplayPolicy.isScreenOnFully() || !okToAnimate();
-        if (PRINT_ANIM) Slog.i(TAG, "selectRotationAnimation mTopFullscreen="
-                + mTopFullscreenOpaqueWindowState + " rotationAnimation="
-                + (mTopFullscreenOpaqueWindowState == null ?
-                        "0" : mTopFullscreenOpaqueWindowState.getAttrs().rotationAnimation)
-                + " forceJumpcut=" + forceJumpcut);
-        if (forceJumpcut) {
-            anim[0] = R.anim.rotation_animation_jump_exit;
-            anim[1] = R.anim.rotation_animation_enter;
-            return;
-        }
-        if (mTopFullscreenOpaqueWindowState != null) {
-            int animationHint = mTopFullscreenOpaqueWindowState.getRotationAnimationHint();
-            if (animationHint < 0 && mTopIsFullscreen) {
-                animationHint = mTopFullscreenOpaqueWindowState.getAttrs().rotationAnimation;
-            }
-            switch (animationHint) {
-                case ROTATION_ANIMATION_CROSSFADE:
-                case ROTATION_ANIMATION_SEAMLESS: // Crossfade is fallback for seamless.
-                    anim[0] = R.anim.rotation_animation_xfade_exit;
-                    anim[1] = R.anim.rotation_animation_enter;
-                    break;
-                case ROTATION_ANIMATION_JUMPCUT:
-                    anim[0] = R.anim.rotation_animation_jump_exit;
-                    anim[1] = R.anim.rotation_animation_enter;
-                    break;
-                case ROTATION_ANIMATION_ROTATE:
-                default:
-                    anim[0] = anim[1] = 0;
-                    break;
-            }
-        } else {
-            anim[0] = anim[1] = 0;
-        }
-    }
-
-    @Override
-    public boolean validateRotationAnimationLw(int exitAnimId, int enterAnimId,
-            boolean forceDefault) {
-        switch (exitAnimId) {
-            case R.anim.rotation_animation_xfade_exit:
-            case R.anim.rotation_animation_jump_exit:
-                // These are the only cases that matter.
-                if (forceDefault) {
-                    return false;
-                }
-                int anim[] = new int[2];
-                selectRotationAnimationLw(anim);
-                return (exitAnimId == anim[0] && enterAnimId == anim[1]);
-            default:
-                return true;
-        }
-    }
-
     @Override
     public Animation createHiddenByKeyguardExit(boolean onWallpaper,
             boolean goingToNotificationShade) {
@@ -4173,77 +3344,6 @@
         }
     }
 
-    private final Runnable mClearHideNavigationFlag = new Runnable() {
-        @Override
-        public void run() {
-            synchronized (mWindowManagerFuncs.getWindowManagerLock()) {
-                // Clear flags.
-                mForceClearedSystemUiFlags &=
-                        ~View.SYSTEM_UI_FLAG_HIDE_NAVIGATION;
-            }
-            mWindowManagerFuncs.reevaluateStatusBarVisibility();
-        }
-    };
-
-    /**
-     * Input handler used while nav bar is hidden.  Captures any touch on the screen,
-     * to determine when the nav bar should be shown and prevent applications from
-     * receiving those touches.
-     */
-    final class HideNavInputEventReceiver extends InputEventReceiver {
-        public HideNavInputEventReceiver(InputChannel inputChannel, Looper looper) {
-            super(inputChannel, looper);
-        }
-
-        @Override
-        public void onInputEvent(InputEvent event) {
-            boolean handled = false;
-            try {
-                if (event instanceof MotionEvent
-                        && (event.getSource() & InputDevice.SOURCE_CLASS_POINTER) != 0) {
-                    final MotionEvent motionEvent = (MotionEvent)event;
-                    if (motionEvent.getAction() == MotionEvent.ACTION_DOWN) {
-                        // When the user taps down, we re-show the nav bar.
-                        boolean changed = false;
-                        synchronized (mWindowManagerFuncs.getWindowManagerLock()) {
-                            if (mInputConsumer == null) {
-                                return;
-                            }
-                            // Any user activity always causes us to show the
-                            // navigation controls, if they had been hidden.
-                            // We also clear the low profile and only content
-                            // flags so that tapping on the screen will atomically
-                            // restore all currently hidden screen decorations.
-                            int newVal = mResettingSystemUiFlags |
-                                    View.SYSTEM_UI_FLAG_HIDE_NAVIGATION |
-                                    View.SYSTEM_UI_FLAG_LOW_PROFILE |
-                                    View.SYSTEM_UI_FLAG_FULLSCREEN;
-                            if (mResettingSystemUiFlags != newVal) {
-                                mResettingSystemUiFlags = newVal;
-                                changed = true;
-                            }
-                            // We don't allow the system's nav bar to be hidden
-                            // again for 1 second, to prevent applications from
-                            // spamming us and keeping it from being shown.
-                            newVal = mForceClearedSystemUiFlags |
-                                    View.SYSTEM_UI_FLAG_HIDE_NAVIGATION;
-                            if (mForceClearedSystemUiFlags != newVal) {
-                                mForceClearedSystemUiFlags = newVal;
-                                changed = true;
-                                mHandler.postDelayed(mClearHideNavigationFlag, 1000);
-                            }
-                        }
-                        if (changed) {
-                            mWindowManagerFuncs.reevaluateStatusBarVisibility();
-                        }
-                    }
-                }
-            } finally {
-                finishInputEvent(event, handled);
-            }
-        }
-    }
-
     @Override
     public void setRecentsVisibilityLw(boolean visible) {
         mRecentsVisible = visible;
@@ -4259,1177 +3359,9 @@
         mNavBarVirtualKeyHapticFeedbackEnabled = enabled;
     }
 
-    @Override
-    public int adjustSystemUiVisibilityLw(int visibility) {
-        mStatusBarController.adjustSystemUiVisibilityLw(mLastSystemUiFlags, visibility);
-        mNavigationBarController.adjustSystemUiVisibilityLw(mLastSystemUiFlags, visibility);
-
-        // Reset any bits in mForceClearingStatusBarVisibility that
-        // are now clear.
-        mResettingSystemUiFlags &= visibility;
-        // Clear any bits in the new visibility that are currently being
-        // force cleared, before reporting it.
-        return visibility & ~mResettingSystemUiFlags
-                & ~mForceClearedSystemUiFlags;
-    }
-
-    @Override
-    // TODO: Should probably be moved into DisplayFrames.
-    public boolean getLayoutHintLw(LayoutParams attrs, Rect taskBounds,
-            DisplayFrames displayFrames, boolean floatingStack, Rect outFrame,
-            Rect outContentInsets, Rect outStableInsets,
-            Rect outOutsets, DisplayCutout.ParcelableWrapper outDisplayCutout) {
-        final int fl = PolicyControl.getWindowFlags(null, attrs);
-        final int pfl = attrs.privateFlags;
-        final int requestedSysUiVis = PolicyControl.getSystemUiVisibility(null, attrs);
-        final int sysUiVis = requestedSysUiVis | getImpliedSysUiFlagsForLayout(attrs);
-        final int displayRotation = displayFrames.mRotation;
-
-        final boolean useOutsets = outOutsets != null && shouldUseOutsets(attrs, fl);
-        if (useOutsets) {
-            int outset = ScreenShapeHelper.getWindowOutsetBottomPx(mContext.getResources());
-            if (outset > 0) {
-                if (displayRotation == Surface.ROTATION_0) {
-                    outOutsets.bottom += outset;
-                } else if (displayRotation == Surface.ROTATION_90) {
-                    outOutsets.right += outset;
-                } else if (displayRotation == Surface.ROTATION_180) {
-                    outOutsets.top += outset;
-                } else if (displayRotation == Surface.ROTATION_270) {
-                    outOutsets.left += outset;
-                }
-            }
-        }
-
-        final boolean layoutInScreen = (fl & FLAG_LAYOUT_IN_SCREEN) != 0;
-        final boolean layoutInScreenAndInsetDecor = layoutInScreen &&
-                (fl & FLAG_LAYOUT_INSET_DECOR) != 0;
-        final boolean screenDecor = (pfl & PRIVATE_FLAG_IS_SCREEN_DECOR) != 0;
-
-        if (layoutInScreenAndInsetDecor && !screenDecor) {
-            if ((sysUiVis & View.SYSTEM_UI_FLAG_LAYOUT_HIDE_NAVIGATION) != 0) {
-                outFrame.set(displayFrames.mUnrestricted);
-            } else {
-                outFrame.set(displayFrames.mRestricted);
-            }
-
-            final Rect sf;
-            if (floatingStack) {
-                sf = null;
-            } else {
-                sf = displayFrames.mStable;
-            }
-
-            final Rect cf;
-            if (floatingStack) {
-                cf = null;
-            } else if ((sysUiVis & View.SYSTEM_UI_FLAG_LAYOUT_STABLE) != 0) {
-                if ((fl & FLAG_FULLSCREEN) != 0) {
-                    cf = displayFrames.mStableFullscreen;
-                } else {
-                    cf = displayFrames.mStable;
-                }
-            } else if ((fl & FLAG_FULLSCREEN) != 0 || (fl & FLAG_LAYOUT_IN_OVERSCAN) != 0) {
-                cf = displayFrames.mOverscan;
-            } else {
-                cf = displayFrames.mCurrent;
-            }
-
-            if (taskBounds != null) {
-                outFrame.intersect(taskBounds);
-            }
-            InsetUtils.insetsBetweenFrames(outFrame, cf, outContentInsets);
-            InsetUtils.insetsBetweenFrames(outFrame, sf, outStableInsets);
-            outDisplayCutout.set(displayFrames.mDisplayCutout.calculateRelativeTo(outFrame)
-                    .getDisplayCutout());
-            return mForceShowSystemBars;
-        } else {
-            if (layoutInScreen) {
-                outFrame.set(displayFrames.mUnrestricted);
-            } else {
-                outFrame.set(displayFrames.mStable);
-            }
-            if (taskBounds != null) {
-                outFrame.intersect(taskBounds);
-            }
-
-            outContentInsets.setEmpty();
-            outStableInsets.setEmpty();
-            outDisplayCutout.set(DisplayCutout.NO_CUTOUT);
-            return mForceShowSystemBars;
-        }
-    }
-
-    private boolean shouldUseOutsets(WindowManager.LayoutParams attrs, int fl) {
-        return attrs.type == TYPE_WALLPAPER || (fl & (WindowManager.LayoutParams.FLAG_FULLSCREEN
-                | WindowManager.LayoutParams.FLAG_LAYOUT_IN_OVERSCAN)) != 0;
-    }
-
     /** {@inheritDoc} */
     @Override
-    public void beginLayoutLw(DisplayFrames displayFrames, int uiMode) {
-        displayFrames.onBeginLayout();
-        // TODO(multi-display): This doesn't seem right...Maybe only apply to default display?
-        mSystemGestures.screenWidth = displayFrames.mUnrestricted.width();
-        mSystemGestures.screenHeight = displayFrames.mUnrestricted.height();
-        mDockLayer = 0x10000000;
-        mStatusBarLayer = -1;
-
-        if (displayFrames.mDisplayId == DEFAULT_DISPLAY) {
-            // For purposes of putting out fake window up to steal focus, we will
-            // drive nav being hidden only by whether it is requested.
-            final int sysui = mLastSystemUiFlags;
-            boolean navVisible = (sysui & View.SYSTEM_UI_FLAG_HIDE_NAVIGATION) == 0;
-            boolean navTranslucent = (sysui
-                    & (View.NAVIGATION_BAR_TRANSLUCENT | View.NAVIGATION_BAR_TRANSPARENT)) != 0;
-            boolean immersive = (sysui & View.SYSTEM_UI_FLAG_IMMERSIVE) != 0;
-            boolean immersiveSticky = (sysui & View.SYSTEM_UI_FLAG_IMMERSIVE_STICKY) != 0;
-            boolean navAllowedHidden = immersive || immersiveSticky;
-            navTranslucent &= !immersiveSticky;  // transient trumps translucent
-            boolean isKeyguardShowing = isStatusBarKeyguard() && !mKeyguardOccluded;
-            if (!isKeyguardShowing) {
-                navTranslucent &= areTranslucentBarsAllowed();
-            }
-            boolean statusBarForcesShowingNavigation = !isKeyguardShowing && mStatusBar != null
-                    && (mStatusBar.getAttrs().privateFlags
-                            & PRIVATE_FLAG_STATUS_FORCE_SHOW_NAVIGATION) != 0;
-
-            // When the navigation bar isn't visible, we put up a fake input window to catch all
-            // touch events. This way we can detect when the user presses anywhere to bring back the
-            // nav bar and ensure the application doesn't see the event.
-            if (navVisible || navAllowedHidden) {
-                if (mInputConsumer != null) {
-                    mHandler.sendMessage(
-                            mHandler.obtainMessage(MSG_DISPOSE_INPUT_CONSUMER, mInputConsumer));
-                    mInputConsumer = null;
-                }
-            } else if (mInputConsumer == null && mStatusBar != null && canHideNavigationBar()) {
-                mInputConsumer = mWindowManagerFuncs.createInputConsumer(mHandler.getLooper(),
-                        INPUT_CONSUMER_NAVIGATION,
-                        (channel, looper) -> new HideNavInputEventReceiver(channel, looper),
-                        displayFrames.mDisplayId);
-                // As long as mInputConsumer is active, hover events are not dispatched to the app
-                // and the pointer icon is likely to become stale. Hide it to avoid confusion.
-                InputManager.getInstance().setPointerIconType(PointerIcon.TYPE_NULL);
-            }
-
-            // For purposes of positioning and showing the nav bar, if we have decided that it can't
-            // be hidden (because of the screen aspect ratio), then take that into account.
-            navVisible |= !canHideNavigationBar();
-
-            boolean updateSysUiVisibility = layoutNavigationBar(displayFrames, uiMode, navVisible,
-                    navTranslucent, navAllowedHidden, statusBarForcesShowingNavigation);
-            if (DEBUG_LAYOUT) Slog.i(TAG, "mDock rect:" + displayFrames.mDock);
-            updateSysUiVisibility |= layoutStatusBar(displayFrames, sysui, isKeyguardShowing);
-            if (updateSysUiVisibility) {
-                updateSystemUiVisibilityLw();
-            }
-        }
-        layoutScreenDecorWindows(displayFrames);
-
-        if (displayFrames.mDisplayCutoutSafe.top > displayFrames.mUnrestricted.top) {
-            // Make sure that the zone we're avoiding for the cutout is at least as tall as the
-            // status bar; otherwise fullscreen apps will end up cutting halfway into the status
-            // bar.
-            displayFrames.mDisplayCutoutSafe.top = Math.max(displayFrames.mDisplayCutoutSafe.top,
-                    displayFrames.mStable.top);
-        }
-    }
-
-    private void layoutScreenDecorWindows(DisplayFrames displayFrames) {
-        if (mScreenDecorWindows.isEmpty()) {
-            return;
-        }
-
-        sTmpRect.setEmpty();
-        sTmpDockedFrame.set(displayFrames.mDock);
-
-        final int displayId = displayFrames.mDisplayId;
-        final Rect dockFrame = displayFrames.mDock;
-        final int displayHeight = displayFrames.mDisplayHeight;
-        final int displayWidth = displayFrames.mDisplayWidth;
-
-        for (int i = mScreenDecorWindows.size() - 1; i >= 0; --i) {
-            final WindowState w = mScreenDecorWindows.valueAt(i);
-            if (w.getDisplayId() != displayId || !w.isVisibleLw()) {
-                // Skip if not on the same display or not visible.
-                continue;
-            }
-
-            w.getWindowFrames().setFrames(sTmpDockedFrame /* parentFrame */,
-                    sTmpDockedFrame /* displayFrame */, sTmpDockedFrame /* overscanFrame */,
-                    sTmpDockedFrame /* contentFrame */, sTmpDockedFrame /* visibleFrame */,
-                    sTmpRect /* decorFrame */, sTmpDockedFrame /* stableFrame */,
-                    sTmpDockedFrame /* outsetFrame */);
-            w.getWindowFrames().setDisplayCutout(displayFrames.mDisplayCutout);
-            w.computeFrameLw();
-            final Rect frame = w.getFrameLw();
-
-            if (frame.left <= 0 && frame.top <= 0) {
-                // Docked at left or top.
-                if (frame.bottom >= displayHeight) {
-                    // Docked left.
-                    dockFrame.left = Math.max(frame.right, dockFrame.left);
-                } else if (frame.right >= displayWidth ) {
-                    // Docked top.
-                    dockFrame.top = Math.max(frame.bottom, dockFrame.top);
-                } else {
-                    Slog.w(TAG, "layoutScreenDecorWindows: Ignoring decor win=" + w
-                            + " not docked on left or top of display. frame=" + frame
-                            + " displayWidth=" + displayWidth + " displayHeight=" + displayHeight);
-                }
-            } else if (frame.right >= displayWidth && frame.bottom >= displayHeight) {
-                // Docked at right or bottom.
-                if (frame.top <= 0) {
-                    // Docked right.
-                    dockFrame.right = Math.min(frame.left, dockFrame.right);
-                } else if (frame.left <= 0) {
-                    // Docked bottom.
-                    dockFrame.bottom = Math.min(frame.top, dockFrame.bottom);
-                } else {
-                    Slog.w(TAG, "layoutScreenDecorWindows: Ignoring decor win=" + w
-                            + " not docked on right or bottom" + " of display. frame=" + frame
-                            + " displayWidth=" + displayWidth + " displayHeight=" + displayHeight);
-                }
-            } else {
-                // Screen decor windows are required to be docked on one of the sides of the screen.
-                Slog.w(TAG, "layoutScreenDecorWindows: Ignoring decor win=" + w
-                        + " not docked on one of the sides of the display. frame=" + frame
-                        + " displayWidth=" + displayWidth + " displayHeight=" + displayHeight);
-            }
-        }
-
-        displayFrames.mRestricted.set(dockFrame);
-        displayFrames.mCurrent.set(dockFrame);
-        displayFrames.mVoiceContent.set(dockFrame);
-        displayFrames.mSystem.set(dockFrame);
-        displayFrames.mContent.set(dockFrame);
-        displayFrames.mRestrictedOverscan.set(dockFrame);
-    }
-
-    private boolean layoutStatusBar(DisplayFrames displayFrames, int sysui,
-            boolean isKeyguardShowing) {
-        // decide where the status bar goes ahead of time
-        if (mStatusBar == null) {
-            return false;
-        }
-        // apply any navigation bar insets
-        sTmpRect.setEmpty();
-        mStatusBar.getWindowFrames().setFrames(displayFrames.mUnrestricted /* parentFrame */,
-                displayFrames.mUnrestricted /* displayFrame */,
-                displayFrames.mStable /* overscanFrame */, displayFrames.mStable /* contentFrame */,
-                displayFrames.mStable /* visibleFrame */, sTmpRect /* decorFrame */,
-                displayFrames.mStable /* stableFrame */, displayFrames.mStable /* outsetFrame */);
-        mStatusBar.getWindowFrames().setDisplayCutout(displayFrames.mDisplayCutout);
-        mStatusBarLayer = mStatusBar.getSurfaceLayer();
-
-        // Let the status bar determine its size.
-        mStatusBar.computeFrameLw();
-
-        // For layout, the status bar is always at the top with our fixed height.
-        displayFrames.mStable.top = displayFrames.mUnrestricted.top
-                + mStatusBarHeightForRotation[displayFrames.mRotation];
-        // Make sure the status bar covers the entire cutout height
-        displayFrames.mStable.top = Math.max(displayFrames.mStable.top,
-                displayFrames.mDisplayCutoutSafe.top);
-
-        // Tell the bar controller where the collapsed status bar content is
-        sTmpRect.set(mStatusBar.getContentFrameLw());
-        sTmpRect.intersect(displayFrames.mDisplayCutoutSafe);
-        sTmpRect.top = mStatusBar.getContentFrameLw().top;  // Ignore top display cutout inset
-        sTmpRect.bottom = displayFrames.mStable.top;  // Use collapsed status bar size
-        mStatusBarController.setContentFrame(sTmpRect);
-
-        boolean statusBarTransient = (sysui & View.STATUS_BAR_TRANSIENT) != 0;
-        boolean statusBarTranslucent = (sysui
-                & (View.STATUS_BAR_TRANSLUCENT | View.STATUS_BAR_TRANSPARENT)) != 0;
-        if (!isKeyguardShowing) {
-            statusBarTranslucent &= areTranslucentBarsAllowed();
-        }
-
-        // If the status bar is hidden, we don't want to cause windows behind it to scroll.
-        if (mStatusBar.isVisibleLw() && !statusBarTransient) {
-            // Status bar may go away, so the screen area it occupies is available to apps but just
-            // covering them when the status bar is visible.
-            final Rect dockFrame = displayFrames.mDock;
-            dockFrame.top = displayFrames.mStable.top;
-            displayFrames.mContent.set(dockFrame);
-            displayFrames.mVoiceContent.set(dockFrame);
-            displayFrames.mCurrent.set(dockFrame);
-
-            if (DEBUG_LAYOUT) Slog.v(TAG, "Status bar: " + String.format(
-                    "dock=%s content=%s cur=%s", dockFrame.toString(),
-                    displayFrames.mContent.toString(), displayFrames.mCurrent.toString()));
-
-            if (!mStatusBar.isAnimatingLw() && !statusBarTranslucent
-                    && !mStatusBarController.wasRecentlyTranslucent()) {
-                // If the opaque status bar is currently requested to be visible, and not in the
-                // process of animating on or off, then we can tell the app that it is covered by it.
-                displayFrames.mSystem.top = displayFrames.mStable.top;
-            }
-        }
-        return mStatusBarController.checkHiddenLw();
-    }
-
-    private boolean layoutNavigationBar(DisplayFrames displayFrames, int uiMode, boolean navVisible,
-            boolean navTranslucent, boolean navAllowedHidden,
-            boolean statusBarForcesShowingNavigation) {
-        if (mNavigationBar == null) {
-            return false;
-        }
-
-        final Rect navigationFrame = sTmpNavFrame;
-        boolean transientNavBarShowing = mNavigationBarController.isTransientShowing();
-        // Force the navigation bar to its appropriate place and size. We need to do this directly,
-        // instead of relying on it to bubble up from the nav bar, because this needs to change
-        // atomically with screen rotations.
-        final int rotation = displayFrames.mRotation;
-        final int displayHeight = displayFrames.mDisplayHeight;
-        final int displayWidth = displayFrames.mDisplayWidth;
-        final Rect dockFrame = displayFrames.mDock;
-        mNavigationBarPosition = navigationBarPosition(displayWidth, displayHeight, rotation);
-
-        final Rect cutoutSafeUnrestricted = sTmpRect;
-        cutoutSafeUnrestricted.set(displayFrames.mUnrestricted);
-        cutoutSafeUnrestricted.intersectUnchecked(displayFrames.mDisplayCutoutSafe);
-
-        if (mNavigationBarPosition == NAV_BAR_BOTTOM) {
-            // It's a system nav bar or a portrait screen; nav bar goes on bottom.
-            final int top = cutoutSafeUnrestricted.bottom
-                    - getNavigationBarHeight(rotation, uiMode);
-            // EXPERIMENT TODO(b/113952590): Remove once experiment in bug is completed
-            final int topNavBar = cutoutSafeUnrestricted.bottom
-                    - mExperiments.getNavigationBarFrameHeight();
-            navigationFrame.set(0, topNavBar, displayWidth, displayFrames.mUnrestricted.bottom);
-            // EXPERIMENT END
-            displayFrames.mStable.bottom = displayFrames.mStableFullscreen.bottom = top;
-            if (transientNavBarShowing) {
-                mNavigationBarController.setBarShowingLw(true);
-            } else if (navVisible) {
-                mNavigationBarController.setBarShowingLw(true);
-                dockFrame.bottom = displayFrames.mRestricted.bottom
-                        = displayFrames.mRestrictedOverscan.bottom = top;
-            } else {
-                // We currently want to hide the navigation UI - unless we expanded the status bar.
-                mNavigationBarController.setBarShowingLw(statusBarForcesShowingNavigation);
-            }
-            if (navVisible && !navTranslucent && !navAllowedHidden
-                    && !mNavigationBar.isAnimatingLw()
-                    && !mNavigationBarController.wasRecentlyTranslucent()) {
-                // If the opaque nav bar is currently requested to be visible and not in the process
-                // of animating on or off, then we can tell the app that it is covered by it.
-                displayFrames.mSystem.bottom = top;
-            }
-        } else if (mNavigationBarPosition == NAV_BAR_RIGHT) {
-            // Landscape screen; nav bar goes to the right.
-            final int left = cutoutSafeUnrestricted.right
-                    - getNavigationBarWidth(rotation, uiMode);
-            // EXPERIMENT TODO(b/113952590): Remove once experiment in bug is completed
-            final int leftNavBar = cutoutSafeUnrestricted.right
-                    - mExperiments.getNavigationBarFrameWidth();
-            navigationFrame.set(leftNavBar, 0, displayFrames.mUnrestricted.right, displayHeight);
-            // EXPERIMENT END
-            displayFrames.mStable.right = displayFrames.mStableFullscreen.right = left;
-            if (transientNavBarShowing) {
-                mNavigationBarController.setBarShowingLw(true);
-            } else if (navVisible) {
-                mNavigationBarController.setBarShowingLw(true);
-                dockFrame.right = displayFrames.mRestricted.right
-                        = displayFrames.mRestrictedOverscan.right = left;
-            } else {
-                // We currently want to hide the navigation UI - unless we expanded the status bar.
-                mNavigationBarController.setBarShowingLw(statusBarForcesShowingNavigation);
-            }
-            if (navVisible && !navTranslucent && !navAllowedHidden
-                    && !mNavigationBar.isAnimatingLw()
-                    && !mNavigationBarController.wasRecentlyTranslucent()) {
-                // If the nav bar is currently requested to be visible, and not in the process of
-                // animating on or off, then we can tell the app that it is covered by it.
-                displayFrames.mSystem.right = left;
-            }
-        } else if (mNavigationBarPosition == NAV_BAR_LEFT) {
-            // Seascape screen; nav bar goes to the left.
-            final int right = cutoutSafeUnrestricted.left
-                    + getNavigationBarWidth(rotation, uiMode);
-            // EXPERIMENT TODO(b/113952590): Remove once experiment in bug is completed
-            final int rightNavBar = cutoutSafeUnrestricted.left
-                    + mExperiments.getNavigationBarFrameWidth();
-            navigationFrame.set(displayFrames.mUnrestricted.left, 0, rightNavBar, displayHeight);
-            // EXPERIMENT END
-            displayFrames.mStable.left = displayFrames.mStableFullscreen.left = right;
-            if (transientNavBarShowing) {
-                mNavigationBarController.setBarShowingLw(true);
-            } else if (navVisible) {
-                mNavigationBarController.setBarShowingLw(true);
-                dockFrame.left = displayFrames.mRestricted.left =
-                        displayFrames.mRestrictedOverscan.left = right;
-            } else {
-                // We currently want to hide the navigation UI - unless we expanded the status bar.
-                mNavigationBarController.setBarShowingLw(statusBarForcesShowingNavigation);
-            }
-            if (navVisible && !navTranslucent && !navAllowedHidden
-                    && !mNavigationBar.isAnimatingLw()
-                    && !mNavigationBarController.wasRecentlyTranslucent()) {
-                // If the nav bar is currently requested to be visible, and not in the process of
-                // animating on or off, then we can tell the app that it is covered by it.
-                displayFrames.mSystem.left = right;
-            }
-        }
-
-        // Make sure the content and current rectangles are updated to account for the restrictions
-        // from the navigation bar.
-        displayFrames.mCurrent.set(dockFrame);
-        displayFrames.mVoiceContent.set(dockFrame);
-        displayFrames.mContent.set(dockFrame);
-        mStatusBarLayer = mNavigationBar.getSurfaceLayer();
-        // And compute the final frame.
-        sTmpRect.setEmpty();
-        mNavigationBar.getWindowFrames().setFrames(navigationFrame /* parentFrame */,
-                navigationFrame /* displayFrame */, navigationFrame /* overscanFrame */,
-                displayFrames.mDisplayCutoutSafe /* contentFrame */,
-                navigationFrame /* visibleFrame */, sTmpRect /* decorFrame */,
-                navigationFrame /* stableFrame */,
-                displayFrames.mDisplayCutoutSafe /* outsetFrame */);
-        mNavigationBar.getWindowFrames().setDisplayCutout(displayFrames.mDisplayCutout);
-        mNavigationBar.computeFrameLw();
-        mNavigationBarController.setContentFrame(mNavigationBar.getContentFrameLw());
-
-        if (DEBUG_LAYOUT) Slog.i(TAG, "mNavigationBar frame: " + navigationFrame);
-        return mNavigationBarController.checkHiddenLw();
-    }
-
-    @NavigationBarPosition
-    private int navigationBarPosition(int displayWidth, int displayHeight, int displayRotation) {
-        if (mDefaultDisplayPolicy.navigationBarCanMove() && displayWidth > displayHeight) {
-            if (displayRotation == Surface.ROTATION_270) {
-                return NAV_BAR_LEFT;
-            } else {
-                return NAV_BAR_RIGHT;
-            }
-        }
-        return NAV_BAR_BOTTOM;
-    }
-
-    /** {@inheritDoc} */
-    @Override
-    public int getSystemDecorLayerLw() {
-        if (mStatusBar != null && mStatusBar.isVisibleLw()) {
-            return mStatusBar.getSurfaceLayer();
-        }
-
-        if (mNavigationBar != null && mNavigationBar.isVisibleLw()) {
-            return mNavigationBar.getSurfaceLayer();
-        }
-
-        return 0;
-    }
-
-    private void setAttachedWindowFrames(WindowState win, int fl, int adjust, WindowState attached,
-            boolean insetDecors, Rect pf, Rect df, Rect of, Rect cf, Rect vf,
-            DisplayFrames displayFrames) {
-        if (!win.isInputMethodTarget() && attached.isInputMethodTarget()) {
-            // Here's a special case: if the child window is not the 'dock window'
-            // or input method target, and the window it is attached to is below
-            // the dock window, then the frames we computed for the window it is
-            // attached to can not be used because the dock is effectively part
-            // of the underlying window and the attached window is floating on top
-            // of the whole thing. So, we ignore the attached window and explicitly
-            // compute the frames that would be appropriate without the dock.
-            vf.set(displayFrames.mDock);
-            cf.set(displayFrames.mDock);
-            of.set(displayFrames.mDock);
-            df.set(displayFrames.mDock);
-        } else {
-            // The effective display frame of the attached window depends on whether it is taking
-            // care of insetting its content. If not, we need to use the parent's content frame so
-            // that the entire window is positioned within that content. Otherwise we can use the
-            // overscan frame and let the attached window take care of positioning its content
-            // appropriately.
-            if (adjust != SOFT_INPUT_ADJUST_RESIZE) {
-                // Set the content frame of the attached window to the parent's decor frame
-                // (same as content frame when IME isn't present) if specifically requested by
-                // setting {@link WindowManager.LayoutParams#FLAG_LAYOUT_ATTACHED_IN_DECOR} flag.
-                // Otherwise, use the overscan frame.
-                cf.set((fl & FLAG_LAYOUT_ATTACHED_IN_DECOR) != 0
-                        ? attached.getContentFrameLw() : attached.getOverscanFrameLw());
-            } else {
-                // If the window is resizing, then we want to base the content frame on our attached
-                // content frame to resize...however, things can be tricky if the attached window is
-                // NOT in resize mode, in which case its content frame will be larger.
-                // Ungh. So to deal with that, make sure the content frame we end up using is not
-                // covering the IM dock.
-                cf.set(attached.getContentFrameLw());
-                if (attached.isVoiceInteraction()) {
-                    cf.intersectUnchecked(displayFrames.mVoiceContent);
-                } else if (win.isInputMethodTarget() || attached.isInputMethodTarget()) {
-                    cf.intersectUnchecked(displayFrames.mContent);
-                }
-            }
-            df.set(insetDecors ? attached.getDisplayFrameLw() : cf);
-            of.set(insetDecors ? attached.getOverscanFrameLw() : cf);
-            vf.set(attached.getVisibleFrameLw());
-        }
-        // The LAYOUT_IN_SCREEN flag is used to determine whether the attached window should be
-        // positioned relative to its parent or the entire screen.
-        pf.set((fl & FLAG_LAYOUT_IN_SCREEN) == 0 ? attached.getFrameLw() : df);
-    }
-
-    private void applyStableConstraints(int sysui, int fl, Rect r, DisplayFrames displayFrames) {
-        if ((sysui & View.SYSTEM_UI_FLAG_LAYOUT_STABLE) == 0) {
-            return;
-        }
-        // If app is requesting a stable layout, don't let the content insets go below the stable
-        // values.
-        if ((fl & FLAG_FULLSCREEN) != 0) {
-            r.intersectUnchecked(displayFrames.mStableFullscreen);
-        } else {
-            r.intersectUnchecked(displayFrames.mStable);
-        }
-    }
-
-    private boolean canReceiveInput(WindowState win) {
-        boolean notFocusable =
-                (win.getAttrs().flags & WindowManager.LayoutParams.FLAG_NOT_FOCUSABLE) != 0;
-        boolean altFocusableIm =
-                (win.getAttrs().flags & WindowManager.LayoutParams.FLAG_ALT_FOCUSABLE_IM) != 0;
-        boolean notFocusableForIm = notFocusable ^ altFocusableIm;
-        return !notFocusableForIm;
-    }
-
-    /** {@inheritDoc} */
-    @Override
-    public void layoutWindowLw(WindowState win, WindowState attached, DisplayFrames displayFrames) {
-        // We've already done the navigation bar, status bar, and all screen decor windows. If the
-        // status bar can receive input, we need to layout it again to accommodate for the IME
-        // window.
-        if ((win == mStatusBar && !canReceiveInput(win)) || win == mNavigationBar
-                || mScreenDecorWindows.contains(win)) {
-            return;
-        }
-        final WindowManager.LayoutParams attrs = win.getAttrs();
-        final boolean isDefaultDisplay = win.isDefaultDisplay();
-
-        final int type = attrs.type;
-        final int fl = PolicyControl.getWindowFlags(win, attrs);
-        final int pfl = attrs.privateFlags;
-        final int sim = attrs.softInputMode;
-        final int requestedSysUiFl = PolicyControl.getSystemUiVisibility(null, attrs);
-        final int sysUiFl = requestedSysUiFl | getImpliedSysUiFlagsForLayout(attrs);
-
-        final WindowFrames windowFrames = win.getWindowFrames();
-
-        windowFrames.setHasOutsets(false);
-        sTmpLastParentFrame.set(windowFrames.mParentFrame);
-        final Rect pf = windowFrames.mParentFrame;
-        final Rect df = windowFrames.mDisplayFrame;
-        final Rect of = windowFrames.mOverscanFrame;
-        final Rect cf = windowFrames.mContentFrame;
-        final Rect vf = windowFrames.mVisibleFrame;
-        final Rect dcf = windowFrames.mDecorFrame;
-        final Rect sf = windowFrames.mStableFrame;
-        dcf.setEmpty();
-        windowFrames.setParentFrameWasClippedByDisplayCutout(false);
-        windowFrames.setDisplayCutout(displayFrames.mDisplayCutout);
-
-        final boolean hasNavBar = (isDefaultDisplay && mDefaultDisplayPolicy.hasNavigationBar()
-                && mNavigationBar != null && mNavigationBar.isVisibleLw());
-
-        final int adjust = sim & SOFT_INPUT_MASK_ADJUST;
-
-        final boolean requestedFullscreen = (fl & FLAG_FULLSCREEN) != 0
-                || (requestedSysUiFl & View.SYSTEM_UI_FLAG_FULLSCREEN) != 0;
-
-        final boolean layoutInScreen = (fl & FLAG_LAYOUT_IN_SCREEN) == FLAG_LAYOUT_IN_SCREEN;
-        final boolean layoutInsetDecor = (fl & FLAG_LAYOUT_INSET_DECOR) == FLAG_LAYOUT_INSET_DECOR;
-
-        sf.set(displayFrames.mStable);
-
-        if (type == TYPE_INPUT_METHOD) {
-            vf.set(displayFrames.mDock);
-            cf.set(displayFrames.mDock);
-            of.set(displayFrames.mDock);
-            df.set(displayFrames.mDock);
-            windowFrames.mParentFrame.set(displayFrames.mDock);
-            // IM dock windows layout below the nav bar...
-            pf.bottom = df.bottom = of.bottom = displayFrames.mUnrestricted.bottom;
-            // ...with content insets above the nav bar
-            cf.bottom = vf.bottom = displayFrames.mStable.bottom;
-            // TODO (b/111364446): Support showing IME on non-default displays
-            if (mStatusBar != null && mFocusedWindow == mStatusBar && canReceiveInput(mStatusBar)) {
-                // The status bar forces the navigation bar while it's visible. Make sure the IME
-                // avoids the navigation bar in that case.
-                if (mNavigationBarPosition == NAV_BAR_RIGHT) {
-                    pf.right = df.right = of.right = cf.right = vf.right =
-                            displayFrames.mStable.right;
-                } else if (mNavigationBarPosition == NAV_BAR_LEFT) {
-                    pf.left = df.left = of.left = cf.left = vf.left = displayFrames.mStable.left;
-                }
-            }
-
-            // EXPERIMENT TODO(b/113952590): Remove once experiment in bug is completed
-            // Offset the ime to avoid overlapping with the nav bar
-            mExperiments.offsetWindowFramesForNavBar(mNavigationBarPosition, win);
-            // EXPERIMENT END
-
-            // IM dock windows always go to the bottom of the screen.
-            attrs.gravity = Gravity.BOTTOM;
-            mDockLayer = win.getSurfaceLayer();
-        } else if (type == TYPE_VOICE_INTERACTION) {
-            of.set(displayFrames.mUnrestricted);
-            df.set(displayFrames.mUnrestricted);
-            pf.set(displayFrames.mUnrestricted);
-            if (adjust != SOFT_INPUT_ADJUST_RESIZE) {
-                cf.set(displayFrames.mDock);
-            } else {
-                cf.set(displayFrames.mContent);
-            }
-            if (adjust != SOFT_INPUT_ADJUST_NOTHING) {
-                vf.set(displayFrames.mCurrent);
-            } else {
-                vf.set(cf);
-            }
-        } else if (type == TYPE_WALLPAPER) {
-           layoutWallpaper(displayFrames, pf, df, of, cf);
-        } else if (win == mStatusBar) {
-            of.set(displayFrames.mUnrestricted);
-            df.set(displayFrames.mUnrestricted);
-            pf.set(displayFrames.mUnrestricted);
-            cf.set(displayFrames.mStable);
-            vf.set(displayFrames.mStable);
-
-            if (adjust == SOFT_INPUT_ADJUST_RESIZE) {
-                cf.bottom = displayFrames.mContent.bottom;
-            } else {
-                cf.bottom = displayFrames.mDock.bottom;
-                vf.bottom = displayFrames.mContent.bottom;
-            }
-        } else {
-            dcf.set(displayFrames.mSystem);
-            final boolean inheritTranslucentDecor =
-                    (attrs.privateFlags & PRIVATE_FLAG_INHERIT_TRANSLUCENT_DECOR) != 0;
-            final boolean isAppWindow =
-                    type >= FIRST_APPLICATION_WINDOW && type <= LAST_APPLICATION_WINDOW;
-            final boolean topAtRest =
-                    win == mTopFullscreenOpaqueWindowState && !win.isAnimatingLw();
-            if (isAppWindow && !inheritTranslucentDecor && !topAtRest) {
-                if ((sysUiFl & View.SYSTEM_UI_FLAG_FULLSCREEN) == 0
-                        && (fl & FLAG_FULLSCREEN) == 0
-                        && (fl & FLAG_TRANSLUCENT_STATUS) == 0
-                        && (fl & FLAG_DRAWS_SYSTEM_BAR_BACKGROUNDS) == 0
-                        && (pfl & PRIVATE_FLAG_FORCE_DRAW_STATUS_BAR_BACKGROUND) == 0) {
-                    // Ensure policy decor includes status bar
-                    dcf.top = displayFrames.mStable.top;
-                }
-                if ((fl & FLAG_TRANSLUCENT_NAVIGATION) == 0
-                        && (sysUiFl & View.SYSTEM_UI_FLAG_HIDE_NAVIGATION) == 0
-                        && (fl & FLAG_DRAWS_SYSTEM_BAR_BACKGROUNDS) == 0) {
-                    // Ensure policy decor includes navigation bar
-                    dcf.bottom = displayFrames.mStable.bottom;
-                    dcf.right = displayFrames.mStable.right;
-                }
-            }
-
-            if (layoutInScreen && layoutInsetDecor) {
-                if (DEBUG_LAYOUT) Slog.v(TAG, "layoutWindowLw(" + attrs.getTitle()
-                            + "): IN_SCREEN, INSET_DECOR");
-                // This is the case for a normal activity window: we want it to cover all of the
-                // screen space, and it can take care of moving its contents to account for screen
-                // decorations that intrude into that space.
-                if (attached != null) {
-                    // If this window is attached to another, our display
-                    // frame is the same as the one we are attached to.
-                    setAttachedWindowFrames(win, fl, adjust, attached, true, pf, df, of, cf, vf,
-                            displayFrames);
-                } else {
-                    if (type == TYPE_STATUS_BAR_PANEL || type == TYPE_STATUS_BAR_SUB_PANEL) {
-                        // Status bar panels are the only windows who can go on top of the status
-                        // bar. They are protected by the STATUS_BAR_SERVICE permission, so they
-                        // have the same privileges as the status bar itself.
-                        //
-                        // However, they should still dodge the navigation bar if it exists.
-
-                        pf.left = df.left = of.left = hasNavBar
-                                ? displayFrames.mDock.left : displayFrames.mUnrestricted.left;
-                        pf.top = df.top = of.top = displayFrames.mUnrestricted.top;
-                        pf.right = df.right = of.right = hasNavBar
-                                ? displayFrames.mRestricted.right
-                                : displayFrames.mUnrestricted.right;
-                        pf.bottom = df.bottom = of.bottom = hasNavBar
-                                ? displayFrames.mRestricted.bottom
-                                : displayFrames.mUnrestricted.bottom;
-
-                        if (DEBUG_LAYOUT) Slog.v(TAG, "Laying out status bar window: " + pf);
-                    } else if ((fl & FLAG_LAYOUT_IN_OVERSCAN) != 0
-                            && type >= FIRST_APPLICATION_WINDOW && type <= LAST_SUB_WINDOW) {
-                        // Asking to layout into the overscan region, so give it that pure
-                        // unrestricted area.
-                        of.set(displayFrames.mOverscan);
-                        df.set(displayFrames.mOverscan);
-                        pf.set(displayFrames.mOverscan);
-                    } else if ((sysUiFl & View.SYSTEM_UI_FLAG_LAYOUT_HIDE_NAVIGATION) != 0
-                            && (type >= FIRST_APPLICATION_WINDOW && type <= LAST_SUB_WINDOW
-                            || type == TYPE_VOLUME_OVERLAY)) {
-                        // Asking for layout as if the nav bar is hidden, lets the application
-                        // extend into the unrestricted overscan screen area. We only do this for
-                        // application windows and certain system windows to ensure no window that
-                        // can be above the nav bar can do this.
-                        df.set(displayFrames.mOverscan);
-                        pf.set(displayFrames.mOverscan);
-                        // We need to tell the app about where the frame inside the overscan is, so
-                        // it can inset its content by that amount -- it didn't ask to actually
-                        // extend itself into the overscan region.
-                        of.set(displayFrames.mUnrestricted);
-                    } else {
-                        df.set(displayFrames.mRestrictedOverscan);
-                        pf.set(displayFrames.mRestrictedOverscan);
-                        // We need to tell the app about where the frame inside the overscan
-                        // is, so it can inset its content by that amount -- it didn't ask
-                        // to actually extend itself into the overscan region.
-                        of.set(displayFrames.mUnrestricted);
-                    }
-
-                    if ((fl & FLAG_FULLSCREEN) == 0) {
-                        if (win.isVoiceInteraction()) {
-                            cf.set(displayFrames.mVoiceContent);
-                        } else {
-                            if (adjust != SOFT_INPUT_ADJUST_RESIZE) {
-                                cf.set(displayFrames.mDock);
-                            } else {
-                                cf.set(displayFrames.mContent);
-                            }
-                        }
-                    } else {
-                        // Full screen windows are always given a layout that is as if the status
-                        // bar and other transient decors are gone. This is to avoid bad states when
-                        // moving from a window that is not hiding the status bar to one that is.
-                        cf.set(displayFrames.mRestricted);
-                    }
-                    applyStableConstraints(sysUiFl, fl, cf, displayFrames);
-                    if (adjust != SOFT_INPUT_ADJUST_NOTHING) {
-                        vf.set(displayFrames.mCurrent);
-                    } else {
-                        vf.set(cf);
-                    }
-
-                    // EXPERIMENT TODO(b/113952590): Remove once experiment in bug is completed
-                    mExperiments.offsetWindowFramesForNavBar(mNavigationBarPosition, win);
-                    // EXPERIMENT END
-                }
-            } else if (layoutInScreen || (sysUiFl
-                    & (View.SYSTEM_UI_FLAG_LAYOUT_FULLSCREEN
-                            | View.SYSTEM_UI_FLAG_LAYOUT_HIDE_NAVIGATION)) != 0) {
-                if (DEBUG_LAYOUT) Slog.v(TAG, "layoutWindowLw(" + attrs.getTitle()
-                        + "): IN_SCREEN");
-                // A window that has requested to fill the entire screen just
-                // gets everything, period.
-                if (type == TYPE_STATUS_BAR_PANEL || type == TYPE_STATUS_BAR_SUB_PANEL) {
-                    cf.set(displayFrames.mUnrestricted);
-                    of.set(displayFrames.mUnrestricted);
-                    df.set(displayFrames.mUnrestricted);
-                    pf.set(displayFrames.mUnrestricted);
-                    if (hasNavBar) {
-                        pf.left = df.left = of.left = cf.left = displayFrames.mDock.left;
-                        pf.right = df.right = of.right = cf.right = displayFrames.mRestricted.right;
-                        pf.bottom = df.bottom = of.bottom = cf.bottom =
-                                displayFrames.mRestricted.bottom;
-                    }
-                    if (DEBUG_LAYOUT) Slog.v(TAG, "Laying out IN_SCREEN status bar window: " + pf);
-                } else if (type == TYPE_NAVIGATION_BAR || type == TYPE_NAVIGATION_BAR_PANEL) {
-                    // The navigation bar has Real Ultimate Power.
-                    of.set(displayFrames.mUnrestricted);
-                    df.set(displayFrames.mUnrestricted);
-                    pf.set(displayFrames.mUnrestricted);
-                    if (DEBUG_LAYOUT) Slog.v(TAG, "Laying out navigation bar window: " + pf);
-                } else if ((type == TYPE_SECURE_SYSTEM_OVERLAY || type == TYPE_SCREENSHOT)
-                        && ((fl & FLAG_FULLSCREEN) != 0)) {
-                    // Fullscreen secure system overlays get what they ask for. Screenshot region
-                    // selection overlay should also expand to full screen.
-                    cf.set(displayFrames.mOverscan);
-                    of.set(displayFrames.mOverscan);
-                    df.set(displayFrames.mOverscan);
-                    pf.set(displayFrames.mOverscan);
-                } else if (type == TYPE_BOOT_PROGRESS) {
-                    // Boot progress screen always covers entire display.
-                    cf.set(displayFrames.mOverscan);
-                    of.set(displayFrames.mOverscan);
-                    df.set(displayFrames.mOverscan);
-                    pf.set(displayFrames.mOverscan);
-                } else if ((fl & FLAG_LAYOUT_IN_OVERSCAN) != 0
-                        && type >= FIRST_APPLICATION_WINDOW && type <= LAST_SUB_WINDOW) {
-                    // Asking to layout into the overscan region, so give it that pure unrestricted
-                    // area.
-                    cf.set(displayFrames.mOverscan);
-                    of.set(displayFrames.mOverscan);
-                    df.set(displayFrames.mOverscan);
-                    pf.set(displayFrames.mOverscan);
-                } else if ((sysUiFl & View.SYSTEM_UI_FLAG_LAYOUT_HIDE_NAVIGATION) != 0
-                        && (type == TYPE_STATUS_BAR
-                            || type == TYPE_TOAST
-                            || type == TYPE_DOCK_DIVIDER
-                            || type == TYPE_VOICE_INTERACTION_STARTING
-                            || (type >= FIRST_APPLICATION_WINDOW && type <= LAST_SUB_WINDOW))) {
-                    // Asking for layout as if the nav bar is hidden, lets the
-                    // application extend into the unrestricted screen area.  We
-                    // only do this for application windows (or toasts) to ensure no window that
-                    // can be above the nav bar can do this.
-                    // XXX This assumes that an app asking for this will also
-                    // ask for layout in only content.  We can't currently figure out
-                    // what the screen would be if only laying out to hide the nav bar.
-                    cf.set(displayFrames.mUnrestricted);
-                    of.set(displayFrames.mUnrestricted);
-                    df.set(displayFrames.mUnrestricted);
-                    pf.set(displayFrames.mUnrestricted);
-                } else if ((sysUiFl & View.SYSTEM_UI_FLAG_LAYOUT_FULLSCREEN) != 0) {
-                    of.set(displayFrames.mRestricted);
-                    df.set(displayFrames.mRestricted);
-                    pf.set(displayFrames.mRestricted);
-                    if (adjust != SOFT_INPUT_ADJUST_RESIZE) {
-                        cf.set(displayFrames.mDock);
-                    } else {
-                        cf.set(displayFrames.mContent);
-                    }
-                } else {
-                    cf.set(displayFrames.mRestricted);
-                    of.set(displayFrames.mRestricted);
-                    df.set(displayFrames.mRestricted);
-                    pf.set(displayFrames.mRestricted);
-                }
-
-                applyStableConstraints(sysUiFl, fl, cf,displayFrames);
-
-                if (adjust != SOFT_INPUT_ADJUST_NOTHING) {
-                    vf.set(displayFrames.mCurrent);
-                } else {
-                    vf.set(cf);
-                }
-            } else if (attached != null) {
-                if (DEBUG_LAYOUT) Slog.v(TAG, "layoutWindowLw(" + attrs.getTitle()
-                        + "): attached to " + attached);
-                // A child window should be placed inside of the same visible
-                // frame that its parent had.
-                setAttachedWindowFrames(win, fl, adjust, attached, false, pf, df, of, cf, vf,
-                        displayFrames);
-            } else {
-                if (DEBUG_LAYOUT) Slog.v(TAG, "layoutWindowLw(" + attrs.getTitle() +
-                        "): normal window");
-                // Otherwise, a normal window must be placed inside the content
-                // of all screen decorations.
-                if (type == TYPE_STATUS_BAR_PANEL) {
-                    // Status bar panels can go on
-                    // top of the status bar. They are protected by the STATUS_BAR_SERVICE
-                    // permission, so they have the same privileges as the status bar itself.
-                    cf.set(displayFrames.mRestricted);
-                    of.set(displayFrames.mRestricted);
-                    df.set(displayFrames.mRestricted);
-                    pf.set(displayFrames.mRestricted);
-                } else if (type == TYPE_TOAST || type == TYPE_SYSTEM_ALERT) {
-                    // These dialogs are stable to interim decor changes.
-                    cf.set(displayFrames.mStable);
-                    of.set(displayFrames.mStable);
-                    df.set(displayFrames.mStable);
-                    pf.set(displayFrames.mStable);
-                } else {
-                    pf.set(displayFrames.mContent);
-                    if (win.isVoiceInteraction()) {
-                        cf.set(displayFrames.mVoiceContent);
-                        of.set(displayFrames.mVoiceContent);
-                        df.set(displayFrames.mVoiceContent);
-                    } else if (adjust != SOFT_INPUT_ADJUST_RESIZE) {
-                        cf.set(displayFrames.mDock);
-                        of.set(displayFrames.mDock);
-                        df.set(displayFrames.mDock);
-                    } else {
-                        cf.set(displayFrames.mContent);
-                        of.set(displayFrames.mContent);
-                        df.set(displayFrames.mContent);
-                    }
-                    if (adjust != SOFT_INPUT_ADJUST_NOTHING) {
-                        vf.set(displayFrames.mCurrent);
-                    } else {
-                        vf.set(cf);
-                    }
-                }
-            }
-        }
-
-        final int cutoutMode = attrs.layoutInDisplayCutoutMode;
-        final boolean attachedInParent = attached != null && !layoutInScreen;
-        final boolean requestedHideNavigation =
-                (requestedSysUiFl & View.SYSTEM_UI_FLAG_HIDE_NAVIGATION) != 0;
-
-        // TYPE_BASE_APPLICATION windows are never considered floating here because they don't get
-        // cropped / shifted to the displayFrame in WindowState.
-        final boolean floatingInScreenWindow = !attrs.isFullscreen() && layoutInScreen
-                && type != TYPE_BASE_APPLICATION;
-
-        // Ensure that windows with a DEFAULT or NEVER display cutout mode are laid out in
-        // the cutout safe zone.
-        if (cutoutMode != LAYOUT_IN_DISPLAY_CUTOUT_MODE_ALWAYS) {
-            final Rect displayCutoutSafeExceptMaybeBars = sTmpDisplayCutoutSafeExceptMaybeBarsRect;
-            displayCutoutSafeExceptMaybeBars.set(displayFrames.mDisplayCutoutSafe);
-            if (layoutInScreen && layoutInsetDecor && !requestedFullscreen
-                    && cutoutMode == LAYOUT_IN_DISPLAY_CUTOUT_MODE_DEFAULT) {
-                // At the top we have the status bar, so apps that are
-                // LAYOUT_IN_SCREEN | LAYOUT_INSET_DECOR but not FULLSCREEN
-                // already expect that there's an inset there and we don't need to exclude
-                // the window from that area.
-                displayCutoutSafeExceptMaybeBars.top = Integer.MIN_VALUE;
-            }
-            if (layoutInScreen && layoutInsetDecor && !requestedHideNavigation
-                    && cutoutMode == LAYOUT_IN_DISPLAY_CUTOUT_MODE_DEFAULT) {
-                // Same for the navigation bar.
-                switch (mNavigationBarPosition) {
-                    case NAV_BAR_BOTTOM:
-                        displayCutoutSafeExceptMaybeBars.bottom = Integer.MAX_VALUE;
-                        break;
-                    case NAV_BAR_RIGHT:
-                        displayCutoutSafeExceptMaybeBars.right = Integer.MAX_VALUE;
-                        break;
-                    case NAV_BAR_LEFT:
-                        displayCutoutSafeExceptMaybeBars.left = Integer.MIN_VALUE;
-                        break;
-                }
-            }
-            if (type == TYPE_INPUT_METHOD && mNavigationBarPosition == NAV_BAR_BOTTOM) {
-                // The IME can always extend under the bottom cutout if the navbar is there.
-                displayCutoutSafeExceptMaybeBars.bottom = Integer.MAX_VALUE;
-            }
-            // Windows that are attached to a parent and laid out in said parent already avoid
-            // the cutout according to that parent and don't need to be further constrained.
-            // Floating IN_SCREEN windows get what they ask for and lay out in the full screen.
-            // They will later be cropped or shifted using the displayFrame in WindowState,
-            // which prevents overlap with the DisplayCutout.
-            if (!attachedInParent && !floatingInScreenWindow) {
-                sTmpRect.set(pf);
-                pf.intersectUnchecked(displayCutoutSafeExceptMaybeBars);
-                windowFrames.setParentFrameWasClippedByDisplayCutout(!sTmpRect.equals(pf));
-            }
-            // Make sure that NO_LIMITS windows clipped to the display don't extend under the
-            // cutout.
-            df.intersectUnchecked(displayCutoutSafeExceptMaybeBars);
-        }
-
-        // Content should never appear in the cutout.
-        cf.intersectUnchecked(displayFrames.mDisplayCutoutSafe);
-
-        // TYPE_SYSTEM_ERROR is above the NavigationBar so it can't be allowed to extend over it.
-        // Also, we don't allow windows in multi-window mode to extend out of the screen.
-        if ((fl & FLAG_LAYOUT_NO_LIMITS) != 0 && type != TYPE_SYSTEM_ERROR
-                && !win.isInMultiWindowMode()) {
-            df.left = df.top = -10000;
-            df.right = df.bottom = 10000;
-            if (type != TYPE_WALLPAPER) {
-                of.left = of.top = cf.left = cf.top = vf.left = vf.top = -10000;
-                of.right = of.bottom = cf.right = cf.bottom = vf.right = vf.bottom = 10000;
-            }
-        }
-
-        // If the device has a chin (e.g. some watches), a dead area at the bottom of the screen we
-        // need to provide information to the clients that want to pretend that you can draw there.
-        // We only want to apply outsets to certain types of windows. For example, we never want to
-        // apply the outsets to floating dialogs, because they wouldn't make sense there.
-        final boolean useOutsets = shouldUseOutsets(attrs, fl);
-        if (isDefaultDisplay && useOutsets) {
-            final Rect osf = windowFrames.mOutsetFrame;
-            osf.set(cf.left, cf.top, cf.right, cf.bottom);
-            windowFrames.setHasOutsets(true);
-            int outset = ScreenShapeHelper.getWindowOutsetBottomPx(mContext.getResources());
-            if (outset > 0) {
-                int rotation = displayFrames.mRotation;
-                if (rotation == Surface.ROTATION_0) {
-                    osf.bottom += outset;
-                } else if (rotation == Surface.ROTATION_90) {
-                    osf.right += outset;
-                } else if (rotation == Surface.ROTATION_180) {
-                    osf.top -= outset;
-                } else if (rotation == Surface.ROTATION_270) {
-                    osf.left -= outset;
-                }
-                if (DEBUG_LAYOUT) Slog.v(TAG, "applying bottom outset of " + outset
-                        + " with rotation " + rotation + ", result: " + osf);
-            }
-        }
-
-        if (DEBUG_LAYOUT) Slog.v(TAG, "Compute frame " + attrs.getTitle()
-                + ": sim=#" + Integer.toHexString(sim)
-                + " attach=" + attached + " type=" + type
-                + String.format(" flags=0x%08x", fl)
-                + " pf=" + pf.toShortString() + " df=" + df.toShortString()
-                + " of=" + of.toShortString()
-                + " cf=" + cf.toShortString() + " vf=" + vf.toShortString()
-                + " dcf=" + dcf.toShortString()
-                + " sf=" + sf.toShortString()
-                + " osf=" + windowFrames.mOutsetFrame.toShortString() + " " + win);
-
-        if (!sTmpLastParentFrame.equals(pf)) {
-            windowFrames.setContentChanged(true);
-        }
-
-        win.computeFrameLw();
-        // Dock windows carve out the bottom of the screen, so normal windows
-        // can't appear underneath them.
-        if (type == TYPE_INPUT_METHOD && win.isVisibleLw()
-                && !win.getGivenInsetsPendingLw()) {
-            offsetInputMethodWindowLw(win, displayFrames);
-        }
-        if (type == TYPE_VOICE_INTERACTION && win.isVisibleLw()
-                && !win.getGivenInsetsPendingLw()) {
-            offsetVoiceInputWindowLw(win, displayFrames);
-        }
-    }
-
-    private void layoutWallpaper(DisplayFrames displayFrames, Rect pf, Rect df, Rect of, Rect cf) {
-        // The wallpaper has Real Ultimate Power, but we want to tell it about the overscan area.
-        df.set(displayFrames.mOverscan);
-        pf.set(displayFrames.mOverscan);
-        cf.set(displayFrames.mUnrestricted);
-        of.set(displayFrames.mUnrestricted);
-    }
-
-    private void offsetInputMethodWindowLw(WindowState win, DisplayFrames displayFrames) {
-        int top = Math.max(win.getDisplayFrameLw().top, win.getContentFrameLw().top);
-        top += win.getGivenContentInsetsLw().top;
-        displayFrames.mContent.bottom = Math.min(displayFrames.mContent.bottom, top);
-        displayFrames.mVoiceContent.bottom = Math.min(displayFrames.mVoiceContent.bottom, top);
-        top = win.getVisibleFrameLw().top;
-        top += win.getGivenVisibleInsetsLw().top;
-        displayFrames.mCurrent.bottom = Math.min(displayFrames.mCurrent.bottom, top);
-        if (DEBUG_LAYOUT) Slog.v(TAG, "Input method: mDockBottom="
-                + displayFrames.mDock.bottom + " mContentBottom="
-                + displayFrames.mContent.bottom + " mCurBottom=" + displayFrames.mCurrent.bottom);
-    }
-
-    private void offsetVoiceInputWindowLw(WindowState win, DisplayFrames displayFrames) {
-        int top = Math.max(win.getDisplayFrameLw().top, win.getContentFrameLw().top);
-        top += win.getGivenContentInsetsLw().top;
-        displayFrames.mVoiceContent.bottom = Math.min(displayFrames.mVoiceContent.bottom, top);
-    }
-
-    /** {@inheritDoc} */
-    @Override
-    public void beginPostLayoutPolicyLw(int displayWidth, int displayHeight) {
-        mTopFullscreenOpaqueWindowState = null;
-        mTopFullscreenOpaqueOrDimmingWindowState = null;
-        mTopDockedOpaqueWindowState = null;
-        mTopDockedOpaqueOrDimmingWindowState = null;
-        mForceStatusBar = false;
-        mForceStatusBarFromKeyguard = false;
-        mForceStatusBarTransparent = false;
-        mForcingShowNavBar = false;
-        mForcingShowNavBarLayer = -1;
-
-        mAllowLockscreenWhenOn = false;
-        mShowingDream = false;
-        mWindowSleepTokenNeeded = false;
-    }
-
-    /** {@inheritDoc} */
-    @Override
-    public void applyPostLayoutPolicyLw(WindowState win, WindowManager.LayoutParams attrs,
-            WindowState attached, WindowState imeTarget) {
-        final boolean affectsSystemUi = win.canAffectSystemUiFlags();
-        if (DEBUG_LAYOUT) Slog.i(TAG, "Win " + win + ": affectsSystemUi=" + affectsSystemUi);
-        applyKeyguardPolicyLw(win, imeTarget);
-        final int fl = PolicyControl.getWindowFlags(win, attrs);
-        if (mTopFullscreenOpaqueWindowState == null && affectsSystemUi
-                && attrs.type == TYPE_INPUT_METHOD) {
-            mForcingShowNavBar = true;
-            mForcingShowNavBarLayer = win.getSurfaceLayer();
-        }
-        if (attrs.type == TYPE_STATUS_BAR) {
-            if ((attrs.privateFlags & PRIVATE_FLAG_KEYGUARD) != 0) {
-                mForceStatusBarFromKeyguard = true;
-            }
-            if ((attrs.privateFlags & PRIVATE_FLAG_FORCE_STATUS_BAR_VISIBLE_TRANSPARENT) != 0) {
-                mForceStatusBarTransparent = true;
-            }
-        }
-
-        boolean appWindow = attrs.type >= FIRST_APPLICATION_WINDOW
-                && attrs.type < FIRST_SYSTEM_WINDOW;
-        final int windowingMode = win.getWindowingMode();
-        final boolean inFullScreenOrSplitScreenSecondaryWindowingMode =
-                windowingMode == WINDOWING_MODE_FULLSCREEN
-                        || windowingMode == WINDOWING_MODE_SPLIT_SCREEN_SECONDARY;
-        if (mTopFullscreenOpaqueWindowState == null && affectsSystemUi) {
-            if ((fl & FLAG_FORCE_NOT_FULLSCREEN) != 0) {
-                mForceStatusBar = true;
-            }
-            if (attrs.type == TYPE_DREAM) {
-                // If the lockscreen was showing when the dream started then wait
-                // for the dream to draw before hiding the lockscreen.
-                if (!mDreamingLockscreen
-                        || (win.isVisibleLw() && win.hasDrawnLw())) {
-                    mShowingDream = true;
-                    appWindow = true;
-                }
-            }
-
-            // For app windows that are not attached, we decide if all windows in the app they
-            // represent should be hidden or if we should hide the lockscreen. For attached app
-            // windows we defer the decision to the window it is attached to.
-            if (appWindow && attached == null) {
-                if (attrs.isFullscreen() && inFullScreenOrSplitScreenSecondaryWindowingMode) {
-                    if (DEBUG_LAYOUT) Slog.v(TAG, "Fullscreen window: " + win);
-                    mTopFullscreenOpaqueWindowState = win;
-                    if (mTopFullscreenOpaqueOrDimmingWindowState == null) {
-                        mTopFullscreenOpaqueOrDimmingWindowState = win;
-                    }
-                    if ((fl & FLAG_ALLOW_LOCK_WHILE_SCREEN_ON) != 0) {
-                        mAllowLockscreenWhenOn = true;
-                    }
-                }
-            }
-        }
-
-        // Voice interaction overrides both top fullscreen and top docked.
-        if (affectsSystemUi && win.getAttrs().type == TYPE_VOICE_INTERACTION) {
-            if (mTopFullscreenOpaqueWindowState == null) {
-                mTopFullscreenOpaqueWindowState = win;
-                if (mTopFullscreenOpaqueOrDimmingWindowState == null) {
-                    mTopFullscreenOpaqueOrDimmingWindowState = win;
-                }
-            }
-            if (mTopDockedOpaqueWindowState == null) {
-                mTopDockedOpaqueWindowState = win;
-                if (mTopDockedOpaqueOrDimmingWindowState == null) {
-                    mTopDockedOpaqueOrDimmingWindowState = win;
-                }
-            }
-        }
-
-        // Keep track of the window if it's dimming but not necessarily fullscreen.
-        if (mTopFullscreenOpaqueOrDimmingWindowState == null && affectsSystemUi
-                && win.isDimming() && inFullScreenOrSplitScreenSecondaryWindowingMode) {
-            mTopFullscreenOpaqueOrDimmingWindowState = win;
-        }
-
-        // We need to keep track of the top "fullscreen" opaque window for the docked stack
-        // separately, because both the "real fullscreen" opaque window and the one for the docked
-        // stack can control View.SYSTEM_UI_FLAG_LIGHT_STATUS_BAR.
-        if (mTopDockedOpaqueWindowState == null && affectsSystemUi && appWindow && attached == null
-                && attrs.isFullscreen() && windowingMode == WINDOWING_MODE_SPLIT_SCREEN_PRIMARY) {
-            mTopDockedOpaqueWindowState = win;
-            if (mTopDockedOpaqueOrDimmingWindowState == null) {
-                mTopDockedOpaqueOrDimmingWindowState = win;
-            }
-        }
-
-        // Also keep track of any windows that are dimming but not necessarily fullscreen in the
-        // docked stack.
-        if (mTopDockedOpaqueOrDimmingWindowState == null && affectsSystemUi && win.isDimming()
-                && windowingMode == WINDOWING_MODE_SPLIT_SCREEN_PRIMARY) {
-            mTopDockedOpaqueOrDimmingWindowState = win;
-        }
-
-        // Take note if a window wants to acquire a sleep token.
-        if ((attrs.privateFlags & PRIVATE_FLAG_ACQUIRES_SLEEP_TOKEN) != 0
-                && win.canAcquireSleepToken()) {
-            mWindowSleepTokenNeeded = true;
-        }
-    }
-
-    private void applyKeyguardPolicyLw(WindowState win, WindowState imeTarget) {
+    public void applyKeyguardPolicyLw(WindowState win, WindowState imeTarget) {
         if (canBeHiddenByKeyguardLw(win)) {
             if (shouldBeHiddenByKeyguard(win, imeTarget)) {
                 win.hideLw(false /* doAnimation */);
@@ -5441,148 +3373,9 @@
 
     /** {@inheritDoc} */
     @Override
-    public int finishPostLayoutPolicyLw() {
-        int changes = 0;
-        boolean topIsFullscreen = false;
-
-        final WindowManager.LayoutParams lp = (mTopFullscreenOpaqueWindowState != null)
-                ? mTopFullscreenOpaqueWindowState.getAttrs()
-                : null;
-
-        // If we are not currently showing a dream then remember the current
-        // lockscreen state.  We will use this to determine whether the dream
-        // started while the lockscreen was showing and remember this state
-        // while the dream is showing.
-        if (!mShowingDream) {
-            mDreamingLockscreen = isKeyguardShowingAndNotOccluded();
-            if (mDreamingSleepTokenNeeded) {
-                mDreamingSleepTokenNeeded = false;
-                mHandler.obtainMessage(MSG_UPDATE_DREAMING_SLEEP_TOKEN, 0, 1).sendToTarget();
-            }
-        } else {
-            if (!mDreamingSleepTokenNeeded) {
-                mDreamingSleepTokenNeeded = true;
-                mHandler.obtainMessage(MSG_UPDATE_DREAMING_SLEEP_TOKEN, 1, 1).sendToTarget();
-            }
-        }
-
-        if (mStatusBar != null) {
-            if (DEBUG_LAYOUT) Slog.i(TAG, "force=" + mForceStatusBar
-                    + " forcefkg=" + mForceStatusBarFromKeyguard
-                    + " top=" + mTopFullscreenOpaqueWindowState);
-            boolean shouldBeTransparent = mForceStatusBarTransparent
-                    && !mForceStatusBar
-                    && !mForceStatusBarFromKeyguard;
-            if (!shouldBeTransparent) {
-                mStatusBarController.setShowTransparent(false /* transparent */);
-            } else if (!mStatusBar.isVisibleLw()) {
-                mStatusBarController.setShowTransparent(true /* transparent */);
-            }
-
-            boolean statusBarForcesShowingNavigation
-                    = (mStatusBar.getAttrs().privateFlags
-                            & PRIVATE_FLAG_STATUS_FORCE_SHOW_NAVIGATION) != 0;
-            boolean topAppHidesStatusBar = topAppHidesStatusBar();
-            if (mForceStatusBar || mForceStatusBarFromKeyguard || mForceStatusBarTransparent
-                    || statusBarForcesShowingNavigation) {
-                if (DEBUG_LAYOUT) Slog.v(TAG, "Showing status bar: forced");
-                if (mStatusBarController.setBarShowingLw(true)) {
-                    changes |= FINISH_LAYOUT_REDO_LAYOUT;
-                }
-                // Maintain fullscreen layout until incoming animation is complete.
-                topIsFullscreen = mTopIsFullscreen && mStatusBar.isAnimatingLw();
-                // Transient status bar is not allowed if status bar is on lockscreen or status bar
-                // is expecting the navigation keys from the user.
-                if ((mForceStatusBarFromKeyguard || statusBarForcesShowingNavigation)
-                        && mStatusBarController.isTransientShowing()) {
-                    mStatusBarController.updateVisibilityLw(false /*transientAllowed*/,
-                            mLastSystemUiFlags, mLastSystemUiFlags);
-                }
-            } else if (mTopFullscreenOpaqueWindowState != null) {
-                topIsFullscreen = topAppHidesStatusBar;
-                // The subtle difference between the window for mTopFullscreenOpaqueWindowState
-                // and mTopIsFullscreen is that mTopIsFullscreen is set only if the window
-                // has the FLAG_FULLSCREEN set.  Not sure if there is another way that to be the
-                // case though.
-                if (mStatusBarController.isTransientShowing()) {
-                    if (mStatusBarController.setBarShowingLw(true)) {
-                        changes |= FINISH_LAYOUT_REDO_LAYOUT;
-                    }
-                } else if (topIsFullscreen
-                        && !mWindowManagerInternal.isStackVisible(WINDOWING_MODE_FREEFORM)
-                        && !mWindowManagerInternal.isStackVisible(
-                                WINDOWING_MODE_SPLIT_SCREEN_PRIMARY)) {
-                    if (DEBUG_LAYOUT) Slog.v(TAG, "** HIDING status bar");
-                    if (mStatusBarController.setBarShowingLw(false)) {
-                        changes |= FINISH_LAYOUT_REDO_LAYOUT;
-                    } else {
-                        if (DEBUG_LAYOUT) Slog.v(TAG, "Status bar already hiding");
-                    }
-                } else {
-                    if (DEBUG_LAYOUT) Slog.v(TAG, "** SHOWING status bar: top is not fullscreen");
-                    if (mStatusBarController.setBarShowingLw(true)) {
-                        changes |= FINISH_LAYOUT_REDO_LAYOUT;
-                    }
-                    topAppHidesStatusBar = false;
-                }
-            }
-            mStatusBarController.setTopAppHidesStatusBar(topAppHidesStatusBar);
-        }
-
-        if (mTopIsFullscreen != topIsFullscreen) {
-            if (!topIsFullscreen) {
-                // Force another layout when status bar becomes fully shown.
-                changes |= FINISH_LAYOUT_REDO_LAYOUT;
-            }
-            mTopIsFullscreen = topIsFullscreen;
-        }
-
-        if ((updateSystemUiVisibilityLw()&SYSTEM_UI_CHANGING_LAYOUT) != 0) {
-            // If the navigation bar has been hidden or shown, we need to do another
-            // layout pass to update that window.
-            changes |= FINISH_LAYOUT_REDO_LAYOUT;
-        }
-
-        if (mShowingDream != mLastShowingDream) {
-            mLastShowingDream = mShowingDream;
-            mWindowManagerFuncs.notifyShowingDreamChanged();
-        }
-
-        updateWindowSleepToken();
-
-        // update since mAllowLockscreenWhenOn might have changed
-        updateLockScreenTimeout();
-        return changes;
-    }
-
-    private void updateWindowSleepToken() {
-        if (mWindowSleepTokenNeeded && !mLastWindowSleepTokenNeeded) {
-            mHandler.removeCallbacks(mReleaseSleepTokenRunnable);
-            mHandler.post(mAcquireSleepTokenRunnable);
-        } else if (!mWindowSleepTokenNeeded && mLastWindowSleepTokenNeeded) {
-            mHandler.removeCallbacks(mAcquireSleepTokenRunnable);
-            mHandler.post(mReleaseSleepTokenRunnable);
-        }
-        mLastWindowSleepTokenNeeded = mWindowSleepTokenNeeded;
-    }
-
-    /**
-     * @return Whether the top app should hide the statusbar based on the top fullscreen opaque
-     *         window.
-     */
-    private boolean topAppHidesStatusBar() {
-        if (mTopFullscreenOpaqueWindowState == null) {
-            return false;
-        }
-        final int fl = PolicyControl.getWindowFlags(null,
-                mTopFullscreenOpaqueWindowState.getAttrs());
-        if (localLOGV) {
-            Slog.d(TAG, "frame: " + mTopFullscreenOpaqueWindowState.getFrameLw());
-            Slog.d(TAG, "attr: " + mTopFullscreenOpaqueWindowState.getAttrs()
-                    + " lp.flags=0x" + Integer.toHexString(fl));
-        }
-        return (fl & LayoutParams.FLAG_FULLSCREEN) != 0
-                || (mLastSystemUiFlags & View.SYSTEM_UI_FLAG_FULLSCREEN) != 0;
+    public void setKeyguardCandidateLw(WindowState win) {
+        mKeyguardCandidate = win;
+        setKeyguardOccludedLw(mKeyguardOccluded, true /* force */);
     }
 
     /**
@@ -5598,19 +3391,19 @@
         if (!isOccluded && changed && showing) {
             mKeyguardOccluded = false;
             mKeyguardDelegate.setOccluded(false, true /* animate */);
-            if (mStatusBar != null) {
-                mStatusBar.getAttrs().privateFlags |= PRIVATE_FLAG_KEYGUARD;
+            if (mKeyguardCandidate != null) {
+                mKeyguardCandidate.getAttrs().privateFlags |= PRIVATE_FLAG_KEYGUARD;
                 if (!mKeyguardDelegate.hasLockscreenWallpaper()) {
-                    mStatusBar.getAttrs().flags |= FLAG_SHOW_WALLPAPER;
+                    mKeyguardCandidate.getAttrs().flags |= FLAG_SHOW_WALLPAPER;
                 }
             }
             return true;
         } else if (isOccluded && changed && showing) {
             mKeyguardOccluded = true;
             mKeyguardDelegate.setOccluded(true, false /* animate */);
-            if (mStatusBar != null) {
-                mStatusBar.getAttrs().privateFlags &= ~PRIVATE_FLAG_KEYGUARD;
-                mStatusBar.getAttrs().flags &= ~FLAG_SHOW_WALLPAPER;
+            if (mKeyguardCandidate != null) {
+                mKeyguardCandidate.getAttrs().privateFlags &= ~PRIVATE_FLAG_KEYGUARD;
+                mKeyguardCandidate.getAttrs().flags &= ~FLAG_SHOW_WALLPAPER;
             }
             return true;
         } else if (changed) {
@@ -5622,28 +3415,6 @@
         }
     }
 
-    private boolean isStatusBarKeyguard() {
-        return mStatusBar != null
-                && (mStatusBar.getAttrs().privateFlags & PRIVATE_FLAG_KEYGUARD) != 0;
-    }
-
-    @Override
-    public boolean allowAppAnimationsLw() {
-        return !mShowingDream;
-    }
-
-    @Override
-    public int focusChangedLw(WindowState lastFocus, WindowState newFocus) {
-        mFocusedWindow = newFocus;
-        mLastFocusedWindow = lastFocus;
-        if ((updateSystemUiVisibilityLw() & SYSTEM_UI_CHANGING_LAYOUT) != 0) {
-            // If the navigation bar has been hidden or shown, we need to do another
-            // layout pass to update that window.
-            return FINISH_LAYOUT_REDO_LAYOUT;
-        }
-        return 0;
-    }
-
     /** {@inheritDoc} */
     @Override
     public void notifyLidSwitchChanged(long whenNanos, boolean lidOpen) {
@@ -6469,57 +4240,11 @@
                 // current user.
                 mSettingsObserver.onChange(false);
                 mDefaultDisplayRotation.onUserSwitch();
-
-                // force a re-application of focused window sysui visibility.
-                // the window may never have been shown for this user
-                // e.g. the keyguard when going through the new-user setup flow
-                synchronized (mWindowManagerFuncs.getWindowManagerLock()) {
-                    mLastSystemUiFlags = 0;
-                    updateSystemUiVisibilityLw();
-                }
+                mWindowManagerFuncs.onUserSwitched();
             }
         }
     };
 
-    private final Runnable mHiddenNavPanic = new Runnable() {
-        @Override
-        public void run() {
-            synchronized (mWindowManagerFuncs.getWindowManagerLock()) {
-                if (!isUserSetupComplete()) {
-                    // Swipe-up for navigation bar is disabled during setup
-                    return;
-                }
-                mPendingPanicGestureUptime = SystemClock.uptimeMillis();
-                if (!isNavBarEmpty(mLastSystemUiFlags)) {
-                    mNavigationBarController.showTransient();
-                }
-            }
-        }
-    };
-
-    private void requestTransientBars(WindowState swipeTarget) {
-        synchronized (mWindowManagerFuncs.getWindowManagerLock()) {
-            if (!isUserSetupComplete()) {
-                // Swipe-up for navigation bar is disabled during setup
-                return;
-            }
-            boolean sb = mStatusBarController.checkShowTransientBarLw();
-            boolean nb = mNavigationBarController.checkShowTransientBarLw()
-                    && !isNavBarEmpty(mLastSystemUiFlags);
-            if (sb || nb) {
-                // Don't show status bar when swiping on already visible navigation bar
-                if (!nb && swipeTarget == mNavigationBar) {
-                    if (DEBUG) Slog.d(TAG, "Not showing transient bar, wrong swipe target");
-                    return;
-                }
-                if (sb) mStatusBarController.showTransient();
-                if (nb) mNavigationBarController.showTransient();
-                mImmersiveModeConfirmation.confirmCurrentPrompt();
-                updateSystemUiVisibilityLw();
-            }
-        }
-    }
-
     // Called on the PowerManager's Notifier thread.
     @Override
     public void startedGoingToSleep(int why) {
@@ -6852,11 +4577,6 @@
     }
 
     @Override
-    public boolean isShowingDreamLw() {
-        return mShowingDream;
-    }
-
-    @Override
     public void startKeyguardExitAnimation(long startTime, long fadeoutDuration) {
         if (mKeyguardDelegate != null) {
             if (DEBUG_KEYGUARD) Slog.d(TAG, "PWM.startKeyguardExitAnimation");
@@ -6864,85 +4584,6 @@
         }
     }
 
-    @Override
-    public void getStableInsetsLw(int displayRotation, int displayWidth, int displayHeight,
-            DisplayCutout displayCutout, Rect outInsets) {
-        outInsets.setEmpty();
-
-        // Navigation bar and status bar.
-        getNonDecorInsetsLw(displayRotation, displayWidth, displayHeight, displayCutout, outInsets);
-        outInsets.top = Math.max(outInsets.top, mStatusBarHeightForRotation[displayRotation]);
-    }
-
-    @Override
-    public void getNonDecorInsetsLw(int displayRotation, int displayWidth, int displayHeight,
-            DisplayCutout displayCutout, Rect outInsets) {
-        outInsets.setEmpty();
-
-        // Only navigation bar
-        if (mDefaultDisplayPolicy.hasNavigationBar()) {
-            int position = navigationBarPosition(displayWidth, displayHeight, displayRotation);
-            if (position == NAV_BAR_BOTTOM) {
-                outInsets.bottom = getNavigationBarHeight(displayRotation, mUiMode);
-            } else if (position == NAV_BAR_RIGHT) {
-                outInsets.right = getNavigationBarWidth(displayRotation, mUiMode);
-            } else if (position == NAV_BAR_LEFT) {
-                outInsets.left = getNavigationBarWidth(displayRotation, mUiMode);
-            }
-        }
-
-        if (displayCutout != null) {
-            outInsets.left += displayCutout.getSafeInsetLeft();
-            outInsets.top += displayCutout.getSafeInsetTop();
-            outInsets.right += displayCutout.getSafeInsetRight();
-            outInsets.bottom += displayCutout.getSafeInsetBottom();
-        }
-    }
-
-    @Override
-    public boolean isNavBarForcedShownLw(WindowState windowState) {
-        return mForceShowSystemBars;
-    }
-
-    @Override
-    public int getNavBarPosition() {
-        // TODO(multi-display): Support system decor on secondary displays.
-        return mNavigationBarPosition;
-    }
-
-    @Override
-    public boolean isDockSideAllowed(int dockSide, int originalDockSide, int displayWidth,
-            int displayHeight, int displayRotation) {
-        final int barPosition = navigationBarPosition(displayWidth, displayHeight, displayRotation);
-        return isDockSideAllowed(dockSide, originalDockSide, barPosition,
-                mDefaultDisplayPolicy.navigationBarCanMove());
-    }
-
-    @VisibleForTesting
-    static boolean isDockSideAllowed(int dockSide, int originalDockSide,
-            int navBarPosition, boolean navigationBarCanMove) {
-        if (dockSide == DOCKED_TOP) {
-            return true;
-        }
-
-        if (navigationBarCanMove) {
-            // Only allow the dockside opposite to the nav bar position in landscape
-            return dockSide == DOCKED_LEFT && navBarPosition == NAV_BAR_RIGHT
-                    || dockSide == DOCKED_RIGHT && navBarPosition == NAV_BAR_LEFT;
-        }
-
-        // Side is the same as original side
-        if (dockSide == originalDockSide) {
-            return true;
-        }
-
-        // Only if original docked side was top in portrait will allow left for landscape
-        if (dockSide == DOCKED_LEFT && originalDockSide == DOCKED_TOP) {
-            return true;
-        }
-        return false;
-    }
-
     void sendCloseSystemWindows() {
         PhoneWindow.sendCloseSystemWindows(mContext, null);
     }
@@ -7009,9 +4650,6 @@
             }
         }
 
-        mSystemGestures.systemReady();
-        mImmersiveModeConfirmation.systemReady();
-
         mAutofillManagerInternal = LocalServices.getService(AutofillManagerInternal.class);
     }
 
@@ -7173,10 +4811,22 @@
         mHandler.post(mScreenLockTimeout);
     }
 
+    // TODO (b/113840485): Move this logic to DisplayPolicy when lockscreen supports multi-display.
+    @Override
+    public void setAllowLockscreenWhenOn(int displayId, boolean allow) {
+        if (allow) {
+            mAllowLockscreenWhenOnDisplays.add(displayId);
+        } else {
+            mAllowLockscreenWhenOnDisplays.remove(displayId);
+        }
+        updateLockScreenTimeout();
+    }
+
     private void updateLockScreenTimeout() {
         synchronized (mScreenLockTimeout) {
-            final boolean enable = (mAllowLockscreenWhenOn && mDefaultDisplayPolicy.isAwake() &&
-                    mKeyguardDelegate != null && mKeyguardDelegate.isSecure(mCurrentUserId));
+            final boolean enable = !mAllowLockscreenWhenOnDisplays.isEmpty()
+                    && mDefaultDisplayPolicy.isAwake()
+                    && mKeyguardDelegate != null && mKeyguardDelegate.isSecure(mCurrentUserId);
             if (mLockScreenTimerActive != enable) {
                 if (enable) {
                     if (localLOGV) Log.v(TAG, "setting lockscreen timer");
@@ -7192,21 +4842,6 @@
     }
 
     // TODO (multidisplay): Support multiple displays in WindowManagerPolicy.
-    private void updateDreamingSleepToken(boolean acquire) {
-        if (acquire) {
-            if (mDreamingSleepToken == null) {
-                mDreamingSleepToken = mActivityTaskManagerInternal.acquireSleepToken(
-                        "Dream", DEFAULT_DISPLAY);
-            }
-        } else {
-            if (mDreamingSleepToken != null) {
-                mDreamingSleepToken.release();
-                mDreamingSleepToken = null;
-            }
-        }
-    }
-
-    // TODO (multidisplay): Support multiple displays in WindowManagerPolicy.
     private void updateScreenOffSleepToken(boolean acquire) {
         if (acquire) {
             if (mScreenOffSleepToken == null) {
@@ -7254,6 +4889,11 @@
         }
     }
 
+    @Override
+    public int getUiMode() {
+        return mUiMode;
+    }
+
     void updateRotation(boolean alwaysSendConfiguration) {
         try {
             // Set orientation on WindowManager.
@@ -7510,380 +5150,6 @@
         }
     }
 
-    private int updateSystemUiVisibilityLw() {
-        // If there is no window focused, there will be nobody to handle the events
-        // anyway, so just hang on in whatever state we're in until things settle down.
-        WindowState winCandidate = mFocusedWindow != null ? mFocusedWindow
-                : mTopFullscreenOpaqueWindowState;
-        if (winCandidate == null) {
-            return 0;
-        }
-
-        // The immersive mode confirmation should never affect the system bar visibility, otherwise
-        // it will unhide the navigation bar and hide itself.
-        if (winCandidate.getAttrs().token == mImmersiveModeConfirmation.getWindowToken()) {
-
-            // The immersive mode confirmation took the focus from mLastFocusedWindow which was
-            // controlling the system ui visibility. So if mLastFocusedWindow can still receive
-            // keys, we let it keep controlling the visibility.
-            final boolean lastFocusCanReceiveKeys =
-                    (mLastFocusedWindow != null && mLastFocusedWindow.canReceiveKeys());
-            winCandidate = isStatusBarKeyguard() ? mStatusBar
-                    : lastFocusCanReceiveKeys ? mLastFocusedWindow
-                    : mTopFullscreenOpaqueWindowState;
-            if (winCandidate == null) {
-                return 0;
-            }
-        }
-        final WindowState win = winCandidate;
-        if ((win.getAttrs().privateFlags & PRIVATE_FLAG_KEYGUARD) != 0 && mKeyguardOccluded) {
-            // We are updating at a point where the keyguard has gotten
-            // focus, but we were last in a state where the top window is
-            // hiding it.  This is probably because the keyguard as been
-            // shown while the top window was displayed, so we want to ignore
-            // it here because this is just a very transient change and it
-            // will quickly lose focus once it correctly gets hidden.
-            return 0;
-        }
-
-        int tmpVisibility = PolicyControl.getSystemUiVisibility(win, null)
-                & ~mResettingSystemUiFlags
-                & ~mForceClearedSystemUiFlags;
-        if (mForcingShowNavBar && win.getSurfaceLayer() < mForcingShowNavBarLayer) {
-            tmpVisibility &= ~PolicyControl.adjustClearableFlags(win, View.SYSTEM_UI_CLEARABLE_FLAGS);
-        }
-
-        final int fullscreenVisibility = updateLightStatusBarLw(0 /* vis */,
-                mTopFullscreenOpaqueWindowState, mTopFullscreenOpaqueOrDimmingWindowState);
-        final int dockedVisibility = updateLightStatusBarLw(0 /* vis */,
-                mTopDockedOpaqueWindowState, mTopDockedOpaqueOrDimmingWindowState);
-        mWindowManagerFuncs.getStackBounds(
-                WINDOWING_MODE_UNDEFINED, ACTIVITY_TYPE_HOME, mNonDockedStackBounds);
-        mWindowManagerFuncs.getStackBounds(
-                WINDOWING_MODE_SPLIT_SCREEN_PRIMARY, ACTIVITY_TYPE_STANDARD, mDockedStackBounds);
-        final int visibility = updateSystemBarsLw(win, mLastSystemUiFlags, tmpVisibility);
-        final int diff = visibility ^ mLastSystemUiFlags;
-        final int fullscreenDiff = fullscreenVisibility ^ mLastFullscreenStackSysUiFlags;
-        final int dockedDiff = dockedVisibility ^ mLastDockedStackSysUiFlags;
-        final boolean needsMenu = win.getNeedsMenuLw(mTopFullscreenOpaqueWindowState);
-        if (diff == 0 && fullscreenDiff == 0 && dockedDiff == 0 && mLastFocusNeedsMenu == needsMenu
-                && mFocusedApp == win.getAppToken()
-                && mLastNonDockedStackBounds.equals(mNonDockedStackBounds)
-                && mLastDockedStackBounds.equals(mDockedStackBounds)) {
-            return 0;
-        }
-        mLastSystemUiFlags = visibility;
-        mLastFullscreenStackSysUiFlags = fullscreenVisibility;
-        mLastDockedStackSysUiFlags = dockedVisibility;
-        mLastFocusNeedsMenu = needsMenu;
-        mFocusedApp = win.getAppToken();
-        final Rect fullscreenStackBounds = new Rect(mNonDockedStackBounds);
-        final Rect dockedStackBounds = new Rect(mDockedStackBounds);
-        mHandler.post(new Runnable() {
-                @Override
-                public void run() {
-                    StatusBarManagerInternal statusbar = getStatusBarManagerInternal();
-                    if (statusbar != null) {
-                        statusbar.setSystemUiVisibility(visibility, fullscreenVisibility,
-                                dockedVisibility, 0xffffffff, fullscreenStackBounds,
-                                dockedStackBounds, win.toString());
-                        statusbar.topAppWindowChanged(needsMenu);
-                    }
-                }
-            });
-        return diff;
-    }
-
-    private int updateLightStatusBarLw(int vis, WindowState opaque, WindowState opaqueOrDimming) {
-        final boolean onKeyguard = isStatusBarKeyguard() && !mKeyguardOccluded;
-        final WindowState statusColorWin = onKeyguard ? mStatusBar : opaqueOrDimming;
-        if (statusColorWin != null && (statusColorWin == opaque || onKeyguard)) {
-            // If the top fullscreen-or-dimming window is also the top fullscreen, respect
-            // its light flag.
-            vis &= ~View.SYSTEM_UI_FLAG_LIGHT_STATUS_BAR;
-            vis |= PolicyControl.getSystemUiVisibility(statusColorWin, null)
-                    & View.SYSTEM_UI_FLAG_LIGHT_STATUS_BAR;
-        } else if (statusColorWin != null && statusColorWin.isDimming()) {
-            // Otherwise if it's dimming, clear the light flag.
-            vis &= ~View.SYSTEM_UI_FLAG_LIGHT_STATUS_BAR;
-        }
-        return vis;
-    }
-
-    @VisibleForTesting
-    @Nullable
-    static WindowState chooseNavigationColorWindowLw(WindowState opaque,
-            WindowState opaqueOrDimming, WindowState imeWindow,
-            @NavigationBarPosition int navBarPosition) {
-        // If the IME window is visible and FLAG_DRAWS_SYSTEM_BAR_BACKGROUNDS is set, then IME
-        // window can be navigation color window.
-        final boolean imeWindowCanNavColorWindow = imeWindow != null
-                && imeWindow.isVisibleLw()
-                && navBarPosition == NAV_BAR_BOTTOM
-                && (PolicyControl.getWindowFlags(imeWindow, null)
-                & WindowManager.LayoutParams.FLAG_DRAWS_SYSTEM_BAR_BACKGROUNDS) != 0;
-
-        if (opaque != null && opaqueOrDimming == opaque) {
-            // If the top fullscreen-or-dimming window is also the top fullscreen, respect it
-            // unless IME window is also eligible, since currently the IME window is always show
-            // above the opaque fullscreen app window, regardless of the IME target window.
-            // TODO(b/31559891): Maybe we need to revisit this condition once b/31559891 is fixed.
-            return imeWindowCanNavColorWindow ? imeWindow : opaque;
-        }
-
-        if (opaqueOrDimming == null || !opaqueOrDimming.isDimming()) {
-            // No dimming window is involved. Determine the result only with the IME window.
-            return imeWindowCanNavColorWindow ? imeWindow : null;
-        }
-
-        if (!imeWindowCanNavColorWindow) {
-            // No IME window is involved. Determine the result only with opaqueOrDimming.
-            return opaqueOrDimming;
-        }
-
-        // The IME window and the dimming window are competing.  Check if the dimming window can be
-        // IME target or not.
-        if (LayoutParams.mayUseInputMethod(PolicyControl.getWindowFlags(opaqueOrDimming, null))) {
-            // The IME window is above the dimming window.
-            return imeWindow;
-        } else {
-            // The dimming window is above the IME window.
-            return opaqueOrDimming;
-        }
-    }
-
-    @VisibleForTesting
-    static int updateLightNavigationBarLw(int vis, WindowState opaque, WindowState opaqueOrDimming,
-            WindowState imeWindow, WindowState navColorWin) {
-
-        if (navColorWin != null) {
-            if (navColorWin == imeWindow || navColorWin == opaque) {
-                // Respect the light flag.
-                vis &= ~View.SYSTEM_UI_FLAG_LIGHT_NAVIGATION_BAR;
-                vis |= PolicyControl.getSystemUiVisibility(navColorWin, null)
-                        & View.SYSTEM_UI_FLAG_LIGHT_NAVIGATION_BAR;
-            } else if (navColorWin == opaqueOrDimming && navColorWin.isDimming()) {
-                // Clear the light flag for dimming window.
-                vis &= ~View.SYSTEM_UI_FLAG_LIGHT_NAVIGATION_BAR;
-            }
-        }
-        return vis;
-    }
-
-    private int updateSystemBarsLw(WindowState win, int oldVis, int vis) {
-        final boolean dockedStackVisible =
-                mWindowManagerInternal.isStackVisible(WINDOWING_MODE_SPLIT_SCREEN_PRIMARY);
-        final boolean freeformStackVisible =
-                mWindowManagerInternal.isStackVisible(WINDOWING_MODE_FREEFORM);
-        final boolean resizing = mWindowManagerInternal.isDockedDividerResizing();
-
-        // We need to force system bars when the docked stack is visible, when the freeform stack
-        // is visible but also when we are resizing for the transitions when docked stack
-        // visibility changes.
-        mForceShowSystemBars = dockedStackVisible || freeformStackVisible || resizing;
-        final boolean forceOpaqueStatusBar = mForceShowSystemBars && !mForceStatusBarFromKeyguard;
-
-        // apply translucent bar vis flags
-        WindowState fullscreenTransWin = isStatusBarKeyguard() && !mKeyguardOccluded
-                ? mStatusBar
-                : mTopFullscreenOpaqueWindowState;
-        vis = mStatusBarController.applyTranslucentFlagLw(fullscreenTransWin, vis, oldVis);
-        vis = mNavigationBarController.applyTranslucentFlagLw(fullscreenTransWin, vis, oldVis);
-        final int dockedVis = mStatusBarController.applyTranslucentFlagLw(
-                mTopDockedOpaqueWindowState, 0, 0);
-
-        final boolean fullscreenDrawsStatusBarBackground =
-                drawsStatusBarBackground(vis, mTopFullscreenOpaqueWindowState);
-        final boolean dockedDrawsStatusBarBackground =
-                drawsStatusBarBackground(dockedVis, mTopDockedOpaqueWindowState);
-
-        // prevent status bar interaction from clearing certain flags
-        int type = win.getAttrs().type;
-        boolean statusBarHasFocus = type == TYPE_STATUS_BAR;
-        if (statusBarHasFocus && !isStatusBarKeyguard()) {
-            int flags = View.SYSTEM_UI_FLAG_FULLSCREEN
-                    | View.SYSTEM_UI_FLAG_HIDE_NAVIGATION
-                    | View.SYSTEM_UI_FLAG_IMMERSIVE
-                    | View.SYSTEM_UI_FLAG_IMMERSIVE_STICKY
-                    | View.SYSTEM_UI_FLAG_LIGHT_STATUS_BAR;
-            if (mKeyguardOccluded) {
-                flags |= View.STATUS_BAR_TRANSLUCENT | View.NAVIGATION_BAR_TRANSLUCENT;
-            }
-            vis = (vis & ~flags) | (oldVis & flags);
-        }
-
-        if (fullscreenDrawsStatusBarBackground && dockedDrawsStatusBarBackground) {
-            vis |= View.STATUS_BAR_TRANSPARENT;
-            vis &= ~View.STATUS_BAR_TRANSLUCENT;
-        } else if ((!areTranslucentBarsAllowed() && fullscreenTransWin != mStatusBar)
-                || forceOpaqueStatusBar) {
-            vis &= ~(View.STATUS_BAR_TRANSLUCENT | View.STATUS_BAR_TRANSPARENT);
-        }
-
-        vis = configureNavBarOpacity(vis, dockedStackVisible, freeformStackVisible, resizing);
-
-        // update status bar
-        boolean immersiveSticky =
-                (vis & View.SYSTEM_UI_FLAG_IMMERSIVE_STICKY) != 0;
-        final boolean hideStatusBarWM =
-                mTopFullscreenOpaqueWindowState != null
-                && (PolicyControl.getWindowFlags(mTopFullscreenOpaqueWindowState, null)
-                        & WindowManager.LayoutParams.FLAG_FULLSCREEN) != 0;
-        final boolean hideStatusBarSysui =
-                (vis & View.SYSTEM_UI_FLAG_FULLSCREEN) != 0;
-        final boolean hideNavBarSysui =
-                (vis & View.SYSTEM_UI_FLAG_HIDE_NAVIGATION) != 0;
-
-        final boolean transientStatusBarAllowed = mStatusBar != null
-                && (statusBarHasFocus || (!mForceShowSystemBars
-                        && (hideStatusBarWM || (hideStatusBarSysui && immersiveSticky))));
-
-        final boolean transientNavBarAllowed = mNavigationBar != null
-                && !mForceShowSystemBars && hideNavBarSysui && immersiveSticky;
-
-        final long now = SystemClock.uptimeMillis();
-        final boolean pendingPanic = mPendingPanicGestureUptime != 0
-                && now - mPendingPanicGestureUptime <= PANIC_GESTURE_EXPIRATION;
-        if (pendingPanic && hideNavBarSysui && !isStatusBarKeyguard()
-                && mDefaultDisplayPolicy.isKeyguardDrawComplete()) {
-            // The user performed the panic gesture recently, we're about to hide the bars,
-            // we're no longer on the Keyguard and the screen is ready. We can now request the bars.
-            mPendingPanicGestureUptime = 0;
-            mStatusBarController.showTransient();
-            if (!isNavBarEmpty(vis)) {
-                mNavigationBarController.showTransient();
-            }
-        }
-
-        final boolean denyTransientStatus = mStatusBarController.isTransientShowRequested()
-                && !transientStatusBarAllowed && hideStatusBarSysui;
-        final boolean denyTransientNav = mNavigationBarController.isTransientShowRequested()
-                && !transientNavBarAllowed;
-        if (denyTransientStatus || denyTransientNav || mForceShowSystemBars) {
-            // clear the clearable flags instead
-            clearClearableFlagsLw();
-            vis &= ~View.SYSTEM_UI_CLEARABLE_FLAGS;
-        }
-
-        final boolean immersive = (vis & View.SYSTEM_UI_FLAG_IMMERSIVE) != 0;
-        immersiveSticky = (vis & View.SYSTEM_UI_FLAG_IMMERSIVE_STICKY) != 0;
-        final boolean navAllowedHidden = immersive || immersiveSticky;
-
-        if (hideNavBarSysui && !navAllowedHidden
-                && getWindowLayerLw(win) > getWindowLayerFromTypeLw(TYPE_INPUT_CONSUMER)) {
-            // We can't hide the navbar from this window otherwise the input consumer would not get
-            // the input events.
-            vis = (vis & ~View.SYSTEM_UI_FLAG_HIDE_NAVIGATION);
-        }
-
-        vis = mStatusBarController.updateVisibilityLw(transientStatusBarAllowed, oldVis, vis);
-
-        // update navigation bar
-        boolean oldImmersiveMode = isImmersiveMode(oldVis);
-        boolean newImmersiveMode = isImmersiveMode(vis);
-        if (win != null && oldImmersiveMode != newImmersiveMode) {
-            final String pkg = win.getOwningPackage();
-            mImmersiveModeConfirmation.immersiveModeChangedLw(pkg, newImmersiveMode,
-                    isUserSetupComplete(), isNavBarEmpty(win.getSystemUiVisibility()));
-        }
-
-        vis = mNavigationBarController.updateVisibilityLw(transientNavBarAllowed, oldVis, vis);
-
-        final WindowState navColorWin = chooseNavigationColorWindowLw(
-                mTopFullscreenOpaqueWindowState, mTopFullscreenOpaqueOrDimmingWindowState,
-                mWindowManagerFuncs.getInputMethodWindowLw(), mNavigationBarPosition);
-        vis = updateLightNavigationBarLw(vis, mTopFullscreenOpaqueWindowState,
-                mTopFullscreenOpaqueOrDimmingWindowState,
-                mWindowManagerFuncs.getInputMethodWindowLw(), navColorWin);
-
-        return vis;
-    }
-
-    private boolean drawsStatusBarBackground(int vis, WindowState win) {
-        if (!mStatusBarController.isTransparentAllowed(win)) {
-            return false;
-        }
-        if (win == null) {
-            return true;
-        }
-
-        final boolean drawsSystemBars =
-                (win.getAttrs().flags & FLAG_DRAWS_SYSTEM_BAR_BACKGROUNDS) != 0;
-        final boolean forceDrawsSystemBars =
-                (win.getAttrs().privateFlags & PRIVATE_FLAG_FORCE_DRAW_STATUS_BAR_BACKGROUND) != 0;
-
-        return forceDrawsSystemBars || drawsSystemBars && (vis & View.STATUS_BAR_TRANSLUCENT) == 0;
-    }
-
-    /**
-     * @return the current visibility flags with the nav-bar opacity related flags toggled based
-     *         on the nav bar opacity rules chosen by {@link #mNavBarOpacityMode}.
-     */
-    private int configureNavBarOpacity(int visibility, boolean dockedStackVisible,
-            boolean freeformStackVisible, boolean isDockedDividerResizing) {
-        if (mNavBarOpacityMode == NAV_BAR_OPAQUE_WHEN_FREEFORM_OR_DOCKED) {
-            if (dockedStackVisible || freeformStackVisible || isDockedDividerResizing) {
-                visibility = setNavBarOpaqueFlag(visibility);
-            }
-        } else if (mNavBarOpacityMode == NAV_BAR_TRANSLUCENT_WHEN_FREEFORM_OPAQUE_OTHERWISE) {
-            if (isDockedDividerResizing) {
-                visibility = setNavBarOpaqueFlag(visibility);
-            } else if (freeformStackVisible) {
-                visibility = setNavBarTranslucentFlag(visibility);
-            } else {
-                visibility = setNavBarOpaqueFlag(visibility);
-            }
-        }
-
-        if (!areTranslucentBarsAllowed()) {
-            visibility &= ~View.NAVIGATION_BAR_TRANSLUCENT;
-        }
-        return visibility;
-    }
-
-    private int setNavBarOpaqueFlag(int visibility) {
-        return visibility &= ~(View.NAVIGATION_BAR_TRANSLUCENT | View.NAVIGATION_BAR_TRANSPARENT);
-    }
-
-    private int setNavBarTranslucentFlag(int visibility) {
-        visibility &= ~View.NAVIGATION_BAR_TRANSPARENT;
-        return visibility |= View.NAVIGATION_BAR_TRANSLUCENT;
-    }
-
-    private void clearClearableFlagsLw() {
-        int newVal = mResettingSystemUiFlags | View.SYSTEM_UI_CLEARABLE_FLAGS;
-        if (newVal != mResettingSystemUiFlags) {
-            mResettingSystemUiFlags = newVal;
-            mWindowManagerFuncs.reevaluateStatusBarVisibility();
-        }
-    }
-
-    private boolean isImmersiveMode(int vis) {
-        final int flags = View.SYSTEM_UI_FLAG_IMMERSIVE | View.SYSTEM_UI_FLAG_IMMERSIVE_STICKY;
-        return mNavigationBar != null
-                && (vis & View.SYSTEM_UI_FLAG_HIDE_NAVIGATION) != 0
-                && (vis & flags) != 0
-                && canHideNavigationBar();
-    }
-
-    private static boolean isNavBarEmpty(int systemUiFlags) {
-        final int disableNavigationBar = (View.STATUS_BAR_DISABLE_HOME
-                | View.STATUS_BAR_DISABLE_BACK
-                | View.STATUS_BAR_DISABLE_RECENT);
-
-        return (systemUiFlags & disableNavigationBar) == disableNavigationBar;
-    }
-
-    /**
-     * @return whether the navigation or status bar can be made translucent
-     *
-     * This should return true unless touch exploration is not enabled or
-     * R.boolean.config_enableTranslucentDecor is false.
-     */
-    private boolean areTranslucentBarsAllowed() {
-        return mTranslucentDecorEnabled;
-    }
-
     // Use this instead of checking config_showNavigationBar so that it can be consistently
     // overridden by qemu.hw.mainkeys in the emulator.
     @Override
@@ -7926,44 +5192,8 @@
     }
 
     @Override
-    public boolean shouldRotateSeamlessly(DisplayRotation displayRotation, int oldRotation,
-            int newRotation) {
-        // For the upside down rotation we don't rotate seamlessly as the navigation
-        // bar moves position.
-        // Note most apps (using orientation:sensor or user as opposed to fullSensor)
-        // will not enter the reverse portrait orientation, so actually the
-        // orientation won't change at all.
-        if (oldRotation == displayRotation.getUpsideDownRotation()
-                || newRotation == displayRotation.getUpsideDownRotation()) {
-            return false;
-        }
-        // If the navigation bar can't change sides, then it will
-        // jump when we change orientations and we don't rotate
-        // seamlessly.
-        if (!displayRotation.getDisplayPolicy().navigationBarCanMove()) {
-            return false;
-        }
-
-        final WindowState w = mTopFullscreenOpaqueWindowState;
-        if (w != mFocusedWindow) {
-            return false;
-        }
-
-        // We only enable seamless rotation if the top window has requested
-        // it and is in the fullscreen opaque state. Seamless rotation
-        // requires freezing various Surface states and won't work well
-        // with animations, so we disable it in the animation case for now.
-        if (w != null && !w.isAnimatingLw() &&
-                w.getAttrs().rotationAnimation == ROTATION_ANIMATION_SEAMLESS) {
-            return true;
-        }
-        return false;
-    }
-
-    @Override
     public void writeToProto(ProtoOutputStream proto, long fieldId) {
         final long token = proto.start(fieldId);
-        proto.write(LAST_SYSTEM_UI_FLAGS, mLastSystemUiFlags);
         proto.write(ROTATION_MODE, mDefaultDisplayRotation.getUserRotationMode());
         proto.write(ROTATION, mDefaultDisplayRotation.getUserRotation());
         proto.write(ORIENTATION, mDefaultDisplayRotation.getCurrentAppOrientation());
@@ -7971,30 +5201,9 @@
         proto.write(KEYGUARD_DRAW_COMPLETE, mDefaultDisplayPolicy.isKeyguardDrawComplete());
         proto.write(WINDOW_MANAGER_DRAW_COMPLETE,
                 mDefaultDisplayPolicy.isWindowManagerDrawComplete());
-        if (mFocusedApp != null) {
-            proto.write(FOCUSED_APP_TOKEN, mFocusedApp.toString());
-        }
-        if (mFocusedWindow != null) {
-            mFocusedWindow.writeIdentifierToProto(proto, FOCUSED_WINDOW);
-        }
-        if (mTopFullscreenOpaqueWindowState != null) {
-            mTopFullscreenOpaqueWindowState.writeIdentifierToProto(
-                    proto, TOP_FULLSCREEN_OPAQUE_WINDOW);
-        }
-        if (mTopFullscreenOpaqueOrDimmingWindowState != null) {
-            mTopFullscreenOpaqueOrDimmingWindowState.writeIdentifierToProto(
-                    proto, TOP_FULLSCREEN_OPAQUE_OR_DIMMING_WINDOW);
-        }
         proto.write(KEYGUARD_OCCLUDED, mKeyguardOccluded);
         proto.write(KEYGUARD_OCCLUDED_CHANGED, mKeyguardOccludedChanged);
         proto.write(KEYGUARD_OCCLUDED_PENDING, mPendingKeyguardOccluded);
-        proto.write(FORCE_STATUS_BAR, mForceStatusBar);
-        proto.write(FORCE_STATUS_BAR_FROM_KEYGUARD, mForceStatusBarFromKeyguard);
-        mStatusBarController.writeToProto(proto, STATUS_BAR);
-        mNavigationBarController.writeToProto(proto, NAVIGATION_BAR);
-        if (mDefaultOrientationListener != null) {
-            mDefaultOrientationListener.writeToProto(proto, ORIENTATION_LISTENER);
-        }
         if (mKeyguardDelegate != null) {
             mKeyguardDelegate.writeToProto(proto, KEYGUARD_DELEGATE);
         }
@@ -8008,19 +5217,6 @@
                 pw.print(" mSystemBooted="); pw.println(mSystemBooted);
         pw.print(prefix); pw.print("mCameraLensCoverState=");
                 pw.println(WindowManagerFuncs.cameraLensStateToString(mCameraLensCoverState));
-        if (mLastSystemUiFlags != 0 || mResettingSystemUiFlags != 0
-                || mForceClearedSystemUiFlags != 0) {
-            pw.print(prefix); pw.print("mLastSystemUiFlags=0x");
-                    pw.print(Integer.toHexString(mLastSystemUiFlags));
-                    pw.print(" mResettingSystemUiFlags=0x");
-                    pw.print(Integer.toHexString(mResettingSystemUiFlags));
-                    pw.print(" mForceClearedSystemUiFlags=0x");
-                    pw.println(Integer.toHexString(mForceClearedSystemUiFlags));
-        }
-        if (mLastFocusNeedsMenu) {
-            pw.print(prefix); pw.print("mLastFocusNeedsMenu=");
-                    pw.println(mLastFocusNeedsMenu);
-        }
         pw.print(prefix); pw.print("mWakeGestureEnabledSetting=");
                 pw.println(mWakeGestureEnabledSetting);
 
@@ -8083,50 +5279,11 @@
             final int key = mDisplayHomeButtonHandlers.keyAt(i);
             pw.println(mDisplayHomeButtonHandlers.get(key));
         }
-        pw.print(prefix); pw.print("mDockLayer="); pw.print(mDockLayer);
-                pw.print(" mStatusBarLayer="); pw.println(mStatusBarLayer);
-        pw.print(prefix); pw.print("mShowingDream="); pw.print(mShowingDream);
-                pw.print(" mDreamingLockscreen="); pw.print(mDreamingLockscreen);
-                pw.print(" mDreamingSleepToken="); pw.println(mDreamingSleepToken);
-        if (mStatusBar != null) {
-            pw.print(prefix); pw.print("mStatusBar=");
-                    pw.print(mStatusBar); pw.print(" isStatusBarKeyguard=");
-                    pw.println(isStatusBarKeyguard());
-        }
-        if (mNavigationBar != null) {
-            pw.print(prefix); pw.print("mNavigationBar=");
-                    pw.println(mNavigationBar);
-        }
-        if (mFocusedWindow != null) {
-            pw.print(prefix); pw.print("mFocusedWindow=");
-                    pw.println(mFocusedWindow);
-        }
-        if (mFocusedApp != null) {
-            pw.print(prefix); pw.print("mFocusedApp=");
-                    pw.println(mFocusedApp);
-        }
-        if (mTopFullscreenOpaqueWindowState != null) {
-            pw.print(prefix); pw.print("mTopFullscreenOpaqueWindowState=");
-                    pw.println(mTopFullscreenOpaqueWindowState);
-        }
-        if (mTopFullscreenOpaqueOrDimmingWindowState != null) {
-            pw.print(prefix); pw.print("mTopFullscreenOpaqueOrDimmingWindowState=");
-                    pw.println(mTopFullscreenOpaqueOrDimmingWindowState);
-        }
-        if (mForcingShowNavBar) {
-            pw.print(prefix); pw.print("mForcingShowNavBar=");
-                    pw.println(mForcingShowNavBar); pw.print( "mForcingShowNavBarLayer=");
-                    pw.println(mForcingShowNavBarLayer);
-        }
-        pw.print(prefix); pw.print("mTopIsFullscreen="); pw.print(mTopIsFullscreen);
-                pw.print(" mKeyguardOccluded="); pw.println(mKeyguardOccluded);
-        pw.print(prefix);
-                pw.print("mKeyguardOccludedChanged="); pw.print(mKeyguardOccludedChanged);
+        pw.print(prefix); pw.print("mKeyguardOccluded="); pw.print(mKeyguardOccluded);
+                pw.print(" mKeyguardOccludedChanged="); pw.print(mKeyguardOccludedChanged);
                 pw.print(" mPendingKeyguardOccluded="); pw.println(mPendingKeyguardOccluded);
-        pw.print(prefix); pw.print("mForceStatusBar="); pw.print(mForceStatusBar);
-                pw.print(" mForceStatusBarFromKeyguard=");
-                pw.println(mForceStatusBarFromKeyguard);
-        pw.print(prefix); pw.print("mAllowLockscreenWhenOn="); pw.print(mAllowLockscreenWhenOn);
+        pw.print(prefix); pw.print("mAllowLockscreenWhenOnDisplays=");
+                pw.print(!mAllowLockscreenWhenOnDisplays.isEmpty());
                 pw.print(" mLockScreenTimeout="); pw.print(mLockScreenTimeout);
                 pw.print(" mLockScreenTimerActive="); pw.println(mLockScreenTimerActive);
         if (mHasFeatureLeanback) {
@@ -8139,16 +5296,10 @@
         }
 
         mGlobalKeyManager.dump(prefix, pw);
-        mStatusBarController.dump(pw, prefix);
-        mNavigationBarController.dump(pw, prefix);
-        PolicyControl.dump(prefix, pw);
 
         if (mWakeGestureListener != null) {
             mWakeGestureListener.dump(pw, prefix);
         }
-        if (mDefaultOrientationListener != null) {
-            mDefaultOrientationListener.dump(pw, prefix);
-        }
         if (mBurnInProtectionHelper != null) {
             mBurnInProtectionHelper.dump(prefix, pw);
         }
@@ -8310,11 +5461,6 @@
     }
 
     @Override
-    public void onLockTaskStateChangedLw(int lockTaskState) {
-        mImmersiveModeConfirmation.onLockTaskModeChangedLw(lockTaskState);
-    }
-
-    @Override
     public boolean setAodShowing(boolean aodShowing) {
         if (mAodShowing != aodShowing) {
             mAodShowing = aodShowing;
diff --git a/services/core/java/com/android/server/policy/StatusBarController.java b/services/core/java/com/android/server/policy/StatusBarController.java
deleted file mode 100644
index e6e4d7f..0000000
--- a/services/core/java/com/android/server/policy/StatusBarController.java
+++ /dev/null
@@ -1,127 +0,0 @@
-/*
- * Copyright (C) 2015 The Android Open Source Project
- *
- * Licensed under the Apache License, Version 2.0 (the "License");
- * you may not use this file except in compliance with the License.
- * You may obtain a copy of the License at
- *
- *      http://www.apache.org/licenses/LICENSE-2.0
- *
- * Unless required by applicable law or agreed to in writing, software
- * distributed under the License is distributed on an "AS IS" BASIS,
- * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
- * See the License for the specific language governing permissions and
- * limitations under the License
- */
-
-package com.android.server.policy;
-
-import static android.view.WindowManager.LayoutParams.FLAG_TRANSLUCENT_STATUS;
-import static android.view.WindowManager.LayoutParams.MATCH_PARENT;
-import static com.android.server.wm.WindowManagerInternal.AppTransitionListener;
-
-import android.app.StatusBarManager;
-import android.os.IBinder;
-import android.os.SystemClock;
-import android.view.View;
-import android.view.animation.Animation;
-import android.view.animation.AnimationSet;
-import android.view.animation.Interpolator;
-import android.view.animation.TranslateAnimation;
-
-import com.android.server.LocalServices;
-import com.android.server.statusbar.StatusBarManagerInternal;
-
-/**
- * Implements status bar specific behavior.
- */
-public class StatusBarController extends BarController {
-
-    private final AppTransitionListener mAppTransitionListener
-            = new AppTransitionListener() {
-
-        @Override
-        public void onAppTransitionPendingLocked() {
-            mHandler.post(new Runnable() {
-                @Override
-                public void run() {
-                    StatusBarManagerInternal statusbar = getStatusBarInternal();
-                    if (statusbar != null) {
-                        statusbar.appTransitionPending();
-                    }
-                }
-            });
-        }
-
-        @Override
-        public int onAppTransitionStartingLocked(int transit, IBinder openToken,
-                IBinder closeToken, long duration, long statusBarAnimationStartTime,
-                long statusBarAnimationDuration) {
-            mHandler.post(new Runnable() {
-                @Override
-                public void run() {
-                    StatusBarManagerInternal statusbar = getStatusBarInternal();
-                    if (statusbar != null) {
-                        statusbar.appTransitionStarting(statusBarAnimationStartTime,
-                                statusBarAnimationDuration);
-                    }
-                }
-            });
-            return 0;
-        }
-
-        @Override
-        public void onAppTransitionCancelledLocked(int transit) {
-            mHandler.post(new Runnable() {
-                @Override
-                public void run() {
-                    StatusBarManagerInternal statusbar = getStatusBarInternal();
-                    if (statusbar != null) {
-                        statusbar.appTransitionCancelled();
-                    }
-                }
-            });
-        }
-
-        @Override
-        public void onAppTransitionFinishedLocked(IBinder token) {
-            mHandler.post(new Runnable() {
-                @Override
-                public void run() {
-                    StatusBarManagerInternal statusbar = LocalServices.getService(
-                            StatusBarManagerInternal.class);
-                    if (statusbar != null) {
-                        statusbar.appTransitionFinished();
-                    }
-                }
-            });
-        }
-    };
-
-    public StatusBarController() {
-        super("StatusBar",
-                View.STATUS_BAR_TRANSIENT,
-                View.STATUS_BAR_UNHIDE,
-                View.STATUS_BAR_TRANSLUCENT,
-                StatusBarManager.WINDOW_STATUS_BAR,
-                FLAG_TRANSLUCENT_STATUS,
-                View.STATUS_BAR_TRANSPARENT);
-    }
-
-
-    public void setTopAppHidesStatusBar(boolean hidesStatusBar) {
-        StatusBarManagerInternal statusbar = getStatusBarInternal();
-        if (statusbar != null) {
-            statusbar.setTopAppHidesStatusBar(hidesStatusBar);
-        }
-    }
-
-    @Override
-    protected boolean skipAnimation() {
-        return mWin.getAttrs().height == MATCH_PARENT;
-    }
-
-    public AppTransitionListener getAppTransitionListener() {
-        return mAppTransitionListener;
-    }
-}
diff --git a/services/core/java/com/android/server/policy/WindowManagerPolicy.java b/services/core/java/com/android/server/policy/WindowManagerPolicy.java
index e1c4acf..3d474e3 100644
--- a/services/core/java/com/android/server/policy/WindowManagerPolicy.java
+++ b/services/core/java/com/android/server/policy/WindowManagerPolicy.java
@@ -65,7 +65,6 @@
 
 import android.annotation.IntDef;
 import android.annotation.Nullable;
-import android.app.ActivityManager;
 import android.app.WindowConfiguration;
 import android.content.Context;
 import android.content.res.CompatibilityInfo;
@@ -78,7 +77,6 @@
 import android.util.Slog;
 import android.util.proto.ProtoOutputStream;
 import android.view.Display;
-import android.view.DisplayCutout;
 import android.view.IApplicationToken;
 import android.view.IWindowManager;
 import android.view.InputEventReceiver;
@@ -90,7 +88,6 @@
 
 import com.android.internal.policy.IKeyguardDismissCallback;
 import com.android.internal.policy.IShortcutService;
-import com.android.server.wm.DisplayFrames;
 import com.android.server.wm.DisplayRotation;
 import com.android.server.wm.WindowFrames;
 
@@ -173,11 +170,6 @@
     void onKeyguardOccludedChangedLw(boolean occluded);
 
     /**
-     * Called when the resource overlays change.
-     */
-    default void onOverlayChangedLw(DisplayContentInfo displayContentInfo) {}
-
-    /**
      * Interface to the Window Manager state associated with a particular
      * window.  You can hold on to an instance of this interface from the call
      * to prepareAddWindow() until removeWindow().
@@ -526,11 +518,6 @@
         public static final int CAMERA_LENS_COVERED = 1;
 
         /**
-         * Ask the window manager to re-evaluate the system UI flags.
-         */
-        public void reevaluateStatusBarVisibility();
-
-        /**
          * Add a input consumer which will consume all input events going to any window below it.
          */
         public InputConsumer createInputConsumer(Looper looper, String name,
@@ -573,22 +560,12 @@
         void unregisterPointerEventListener(PointerEventListener listener, int displayId);
 
         /**
-         * @return The content insets of the docked divider window.
-         */
-        int getDockedDividerInsetsLw();
-
-        /**
          * Retrieves the {@param outBounds} from the stack matching the {@param windowingMode} and
          * {@param activityType}.
          */
         void getStackBounds(int windowingMode, int activityType, Rect outBounds);
 
         /**
-         * Notifies window manager that {@link #isShowingDreamLw} has changed.
-         */
-        void notifyShowingDreamChanged();
-
-        /**
          * @return The currently active input method window.
          */
         WindowState getInputMethodWindowLw();
@@ -648,7 +625,15 @@
          */
         void onKeyguardShowingAndNotOccludedChanged();
 
-        DisplayContentInfo getDefaultDisplayContentInfo();
+        /**
+         * Notifies window manager that power key is being pressed.
+         */
+        void onPowerKeyDown(boolean isScreenOn);
+
+        /**
+         * Notifies window manager that user is switched.
+         */
+        void onUserSwitched();
     }
 
     /**
@@ -735,17 +720,6 @@
     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.
-     *
-     * @param attrs The window layout parameters to be modified.  These values
-     * are modified in-place.
-     */
-    public void adjustWindowParamsLw(WindowState win, WindowManager.LayoutParams attrs,
-            boolean hasStatusBarServicePermission);
-
-    /**
      * After the window manager has computed the current configuration based
      * on its knowledge of the display and input devices, it gives the policy
      * a chance to adjust the information contained in it.  If you want to
@@ -941,40 +915,6 @@
     public int getMaxWallpaperLayer();
 
     /**
-     * Return the display width available after excluding any screen
-     * decorations that could never be removed in Honeycomb. That is, system bar or
-     * button bar.
-     */
-    public int getNonDecorDisplayWidth(int fullWidth, int fullHeight, int rotation,
-            int uiMode, int displayId, DisplayCutout displayCutout);
-
-    /**
-     * Return the display height available after excluding any screen
-     * decorations that could never be removed in Honeycomb. That is, system bar or
-     * button bar.
-     */
-    public int getNonDecorDisplayHeight(int fullWidth, int fullHeight, int rotation,
-            int uiMode, int displayId, DisplayCutout displayCutout);
-
-    /**
-     * Return the available screen width that we should report for the
-     * configuration.  This must be no larger than
-     * {@link #getNonDecorDisplayWidth(int, int, int, int, int, DisplayCutout)}; it may be smaller
-     * than that to account for more transient decoration like a status bar.
-     */
-    public int getConfigDisplayWidth(int fullWidth, int fullHeight, int rotation,
-            int uiMode, int displayId, DisplayCutout displayCutout);
-
-    /**
-     * Return the available screen height that we should report for the
-     * configuration.  This must be no larger than
-     * {@link #getNonDecorDisplayHeight(int, int, int, int, int, DisplayCutout)}; it may be smaller
-     * than that to account for more transient decoration like a status bar.
-     */
-    public int getConfigDisplayHeight(int fullWidth, int fullHeight, int rotation,
-            int uiMode, int displayId, DisplayCutout displayCutout);
-
-    /**
      * Return whether the given window can become the Keyguard window. Typically returns true for
      * the StatusBar.
      */
@@ -1013,65 +953,11 @@
             int logo, int windowFlags, Configuration overrideConfig, int displayId);
 
     /**
-     * Prepare for a window being added to the window manager.  You can throw an
-     * exception here to prevent the window being added, or do whatever setup
-     * you need to keep track of the window.
+     * Set or clear a window which can behave as the keyguard.
      *
-     * @param win The window being added.
-     * @param attrs The window's LayoutParams.
-     *
-     * @return {@link WindowManagerGlobal#ADD_OKAY} if the add can proceed, else an
-     *         error code to abort the add.
+     * @param win The window which can behave as the keyguard.
      */
-    public int prepareAddWindowLw(WindowState win,
-            WindowManager.LayoutParams attrs);
-
-    /**
-     * Called when a window is being removed from a window manager.  Must not
-     * throw an exception -- clean up as much as possible.
-     *
-     * @param win The window being removed.
-     */
-    public void removeWindowLw(WindowState win);
-
-    /**
-     * Control the animation to run when a window's state changes.  Return a
-     * non-0 number to force the animation to a specific resource ID, or 0
-     * to use the default animation.
-     *
-     * @param win The window that is changing.
-     * @param transit What is happening to the window: {@link #TRANSIT_ENTER},
-     *                {@link #TRANSIT_EXIT}, {@link #TRANSIT_SHOW}, or
-     *                {@link #TRANSIT_HIDE}.
-     *
-     * @return Resource ID of the actual animation to use, or 0 for none.
-     */
-    public int selectAnimationLw(WindowState win, int transit);
-
-    /**
-     * Determine the animation to run for a rotation transition based on the
-     * top fullscreen windows {@link WindowManager.LayoutParams#rotationAnimation}
-     * and whether it is currently fullscreen and frontmost.
-     *
-     * @param anim The exiting animation resource id is stored in anim[0], the
-     * entering animation resource id is stored in anim[1].
-     */
-    public void selectRotationAnimationLw(int anim[]);
-
-    /**
-     * Validate whether the current top fullscreen has specified the same
-     * {@link WindowManager.LayoutParams#rotationAnimation} value as that
-     * being passed in from the previous top fullscreen window.
-     *
-     * @param exitAnimId exiting resource id from the previous window.
-     * @param enterAnimId entering resource id from the previous window.
-     * @param forceDefault For rotation animations only, if true ignore the
-     * animation values and just return false.
-     * @return true if the previous values are still valid, false if they
-     * should be replaced with the default.
-     */
-    public boolean validateRotationAnimationLw(int exitAnimId, int enterAnimId,
-            boolean forceDefault);
+    void setKeyguardCandidateLw(@Nullable WindowState win);
 
     /**
      * Create and return an animation to re-display a window that was force hidden by Keyguard.
@@ -1148,100 +1034,21 @@
     public KeyEvent dispatchUnhandledKey(WindowState win, KeyEvent event, int policyFlags);
 
     /**
-     * Called when layout of the windows is about to start.
+     * Apply the keyguard policy to a specific window.
      *
-     * @param displayFrames frames of the display we are doing layout on.
-     * @param uiMode The current uiMode in configuration.
+     * @param win The window to apply the keyguard policy.
+     * @param imeTarget The current IME target window.
      */
-    default void beginLayoutLw(DisplayFrames displayFrames, int uiMode) {}
+    void applyKeyguardPolicyLw(WindowState win, WindowState imeTarget);
 
     /**
-     * Returns the bottom-most layer of the system decor, above which no policy decor should
-     * be applied.
-     */
-    public int getSystemDecorLayerLw();
-
-    /**
-     * Called for each window attached to the window manager as layout is proceeding. The
-     * implementation of this function must take care of setting the window's frame, either here or
-     * in finishLayout().
+     * Called when the state of allow-lockscreen-when-on of the display is changed. See
+     * {@link WindowManager.LayoutParams#FLAG_ALLOW_LOCK_WHILE_SCREEN_ON}
      *
-     * @param win The window being positioned.
-     * @param attached For sub-windows, the window it is attached to; this
-     *                 window will already have had layoutWindow() called on it
-     *                 so you can use its Rect.  Otherwise null.
-     * @param displayFrames The display frames.
+     * @param displayId The ID of the display.
+     * @param allow Whether the display allows showing lockscreen when it is on.
      */
-    default void layoutWindowLw(
-            WindowState win, WindowState attached, DisplayFrames displayFrames) {}
-
-    /**
-     * Return the layout hints for a newly added window. These values are computed on the
-     * most recent layout, so they are not guaranteed to be correct.
-     *
-     * @param attrs The LayoutParams of the window.
-     * @param taskBounds The bounds of the task this window is on or {@code null} if no task is
-     *                   associated with the window.
-     * @param displayFrames display frames.
-     * @param floatingStack Whether the window's stack is floating.
-     * @param outFrame The frame of the window.
-     * @param outContentInsets The areas covered by system windows, expressed as positive insets.
-     * @param outStableInsets The areas covered by stable system windows irrespective of their
-     *                        current visibility. Expressed as positive insets.
-     * @param outOutsets The areas that are not real display, but we would like to treat as such.
-     * @param outDisplayCutout The area that has been cut away from the display.
-     * @return Whether to always consume the navigation bar.
-     *         See {@link #isNavBarForcedShownLw(WindowState)}.
-     */
-    default boolean getLayoutHintLw(WindowManager.LayoutParams attrs, Rect taskBounds,
-            DisplayFrames displayFrames, boolean floatingStack,
-            Rect outFrame, Rect outContentInsets, Rect outStableInsets, Rect outOutsets,
-            DisplayCutout.ParcelableWrapper outDisplayCutout) {
-        return false;
-    }
-
-    /**
-     * Called following layout of all windows before each window has policy applied.
-     *
-     * @param displayWidth The current full width of the screen.
-     * @param displayHeight The current full height of the screen.
-     */
-    public void beginPostLayoutPolicyLw(int displayWidth, int displayHeight);
-
-    /**
-     * Called following layout of all window to apply policy to each window.
-     *
-     * @param win The window being positioned.
-     * @param attrs The LayoutParams of the window.
-     * @param attached For sub-windows, the window it is attached to. Otherwise null.
-     */
-    public void applyPostLayoutPolicyLw(WindowState win,
-            WindowManager.LayoutParams attrs, WindowState attached, WindowState imeTarget);
-
-    /**
-     * Called following layout of all windows and after policy has been applied
-     * to each window. If in this function you do
-     * something that may have modified the animation state of another window,
-     * be sure to return non-zero in order to perform another pass through layout.
-     *
-     * @return Return any bit set of {@link #FINISH_LAYOUT_REDO_LAYOUT},
-     * {@link #FINISH_LAYOUT_REDO_CONFIG}, {@link #FINISH_LAYOUT_REDO_WALLPAPER},
-     * or {@link #FINISH_LAYOUT_REDO_ANIM}.
-     */
-    public int finishPostLayoutPolicyLw();
-
-    /**
-     * Return true if it is okay to perform animations for an app transition
-     * that is about to occur. You may return false for this if, for example,
-     * the dream window is currently displayed so the switch should happen
-     * immediately.
-     */
-    public boolean allowAppAnimationsLw();
-
-    /**
-     * A new window has been focused.
-     */
-    public int focusChangedLw(WindowState lastFocus, WindowState newFocus);
+    void setAllowLockscreenWhenOn(int displayId, boolean allow);
 
     /**
      * Called when the device has started waking up.
@@ -1430,8 +1237,6 @@
      */
     public boolean isKeyguardDrawnLw();
 
-    public boolean isShowingDreamLw();
-
     /**
      * Called when the system is mostly done booting to set whether
      * the system should go into safe mode.
@@ -1491,14 +1296,6 @@
     public void keepScreenOnStoppedLw();
 
     /**
-     * Called when a new system UI visibility is being reported, allowing
-     * the policy to adjust what is actually reported.
-     * @param visibility The raw visibility reported by the status bar.
-     * @return The new desired visibility.
-     */
-    public int adjustSystemUiVisibilityLw(int visibility);
-
-    /**
      * Called by System UI to notify of changes to the visibility of Recents.
      */
     public void setRecentsVisibilityLw(boolean visible);
@@ -1548,6 +1345,16 @@
     public void showGlobalActions();
 
     /**
+     * Returns whether the user setup is complete.
+     */
+    boolean isUserSetupComplete();
+
+    /**
+     * Returns the current UI mode.
+     */
+    int getUiMode();
+
+    /**
      * Called when the current user changes. Guaranteed to be called before the broadcast
      * of the new user id is made to all listeners.
      *
@@ -1602,69 +1409,6 @@
     public void startKeyguardExitAnimation(long startTime, long fadeoutDuration);
 
     /**
-     * Calculates the stable insets without running a layout.
-     *
-     * @param displayRotation the current display rotation
-     * @param displayWidth the current display width
-     * @param displayHeight the current display height
-     * @param displayCutout the current display cutout
-     * @param outInsets the insets to return
-     */
-    public void getStableInsetsLw(int displayRotation, int displayWidth, int displayHeight,
-            DisplayCutout displayCutout, Rect outInsets);
-
-
-    /**
-     * @return true if the navigation bar is forced to stay visible
-     */
-    public boolean isNavBarForcedShownLw(WindowState win);
-
-    /**
-     * @return The side of the screen where navigation bar is positioned.
-     * @see #NAV_BAR_LEFT
-     * @see #NAV_BAR_RIGHT
-     * @see #NAV_BAR_BOTTOM
-     */
-    @NavigationBarPosition
-    int getNavBarPosition();
-
-    /**
-     * Calculates the insets for the areas that could never be removed in Honeycomb, i.e. system
-     * bar or button bar. See {@link #getNonDecorDisplayWidth}.
-     *
-     * @param displayRotation the current display rotation
-     * @param displayWidth the current display width
-     * @param displayHeight the current display height
-     * @param displayCutout the current display cutout
-     * @param outInsets the insets to return
-     */
-    public void getNonDecorInsetsLw(int displayRotation, int displayWidth, int displayHeight,
-            DisplayCutout displayCutout, Rect outInsets);
-
-    /**
-     * @param displayRotation the current display rotation
-     * @param displayWidth the current display width
-     * @param displayHeight the current display height
-     * @param dockSide the dockside asking if allowed
-     * @param originalDockSide the side that was original docked to in split screen
-     * @return True if a specified {@param dockSide} is allowed on the current device, or false
-     *         otherwise. It is guaranteed that at least one dock side for a particular orientation
-     *         is allowed, so for example, if DOCKED_RIGHT is not allowed, DOCKED_LEFT is allowed.
-     *         If navigation bar is movable then the docked side would bias towards the
-     *         {@param originalDockSide}.
-     */
-    public boolean isDockSideAllowed(int dockSide, int originalDockSide, int displayWidth,
-            int displayHeight, int displayRotation);
-
-    /**
-     * Called when the configuration has changed, and it's safe to load new values from resources.
-     */
-    public void onConfigurationChanged(DisplayContentInfo displayContentInfo);
-
-    public boolean shouldRotateSeamlessly(DisplayRotation displayRotation,
-            int oldRotation, int newRotation);
-
-    /**
      * Called when System UI has been started.
      */
     void onSystemUiStarted();
@@ -1697,17 +1441,6 @@
     public void requestUserActivityNotification();
 
     /**
-     * Called when the state of lock task mode changes. This should be used to disable immersive
-     * mode confirmation.
-     *
-     * @param lockTaskState the new lock task mode state. One of
-     *                      {@link ActivityManager#LOCK_TASK_MODE_NONE},
-     *                      {@link ActivityManager#LOCK_TASK_MODE_LOCKED},
-     *                      {@link ActivityManager#LOCK_TASK_MODE_PINNED}.
-     */
-    void onLockTaskStateChangedLw(int lockTaskState);
-
-    /**
      * Updates the flag about whether AOD is showing.
      *
      * @return whether the value was changed.
diff --git a/services/core/java/com/android/server/statusbar/StatusBarManagerInternal.java b/services/core/java/com/android/server/statusbar/StatusBarManagerInternal.java
index 095eaa5..a66f0ca 100644
--- a/services/core/java/com/android/server/statusbar/StatusBarManagerInternal.java
+++ b/services/core/java/com/android/server/statusbar/StatusBarManagerInternal.java
@@ -44,36 +44,42 @@
      */
     void showPictureInPictureMenu();
 
-    void setWindowState(int window, int state);
+    void setWindowState(int displayId, int window, int state);
 
     /**
      * Notifies the status bar that an app transition is pending to delay applying some flags with
      * visual impact until {@link #appTransitionReady} is called.
+     *
+     * @param displayId the ID of the display which has this event.
      */
-    void appTransitionPending();
+    void appTransitionPending(int displayId);
 
     /**
      * Notifies the status bar that a pending app transition has been cancelled.
+     *
+     * @param displayId the ID of the display which has this event.
      */
-    void appTransitionCancelled();
+    void appTransitionCancelled(int displayId);
 
     /**
      * Notifies the status bar that an app transition is now being executed.
      *
+     * @param displayId the ID of the display which has this event.
      * @param statusBarAnimationsStartTime the desired start time for all visual animations in the
      *        status bar caused by this app transition in uptime millis
      * @param statusBarAnimationsDuration the duration for all visual animations in the status
      *        bar caused by this app transition in millis
      */
-    void appTransitionStarting(long statusBarAnimationsStartTime, long statusBarAnimationsDuration);
+    void appTransitionStarting(int displayId, long statusBarAnimationsStartTime,
+            long statusBarAnimationsDuration);
 
     void startAssist(Bundle args);
     void onCameraLaunchGestureDetected(int source);
-    void topAppWindowChanged(boolean menuVisible);
-    void setSystemUiVisibility(int vis, int fullscreenStackVis, int dockedStackVis, int mask,
-            Rect fullscreenBounds, Rect dockedBounds, String cause);
+    void topAppWindowChanged(int displayId, boolean menuVisible);
+    void setSystemUiVisibility(int displayId, int vis, int fullscreenStackVis, int dockedStackVis,
+            int mask, Rect fullscreenBounds, Rect dockedBounds, String cause);
     void toggleSplitScreen();
-    void appTransitionFinished();
+    void appTransitionFinished(int displayId);
 
     void toggleRecentApps();
 
diff --git a/services/core/java/com/android/server/statusbar/StatusBarManagerService.java b/services/core/java/com/android/server/statusbar/StatusBarManagerService.java
index 3e07ebe..1eb44a0 100644
--- a/services/core/java/com/android/server/statusbar/StatusBarManagerService.java
+++ b/services/core/java/com/android/server/statusbar/StatusBarManagerService.java
@@ -39,6 +39,7 @@
 import android.util.ArrayMap;
 import android.util.Log;
 import android.util.Slog;
+import android.view.Display;
 
 import com.android.internal.R;
 import com.android.internal.statusbar.IStatusBar;
@@ -237,14 +238,22 @@
         }
 
         @Override
-        public void topAppWindowChanged(boolean menuVisible) {
+        public void topAppWindowChanged(int displayId, boolean menuVisible) {
+            if (displayId != Display.DEFAULT_DISPLAY) {
+                // TODO (b/117478341): Resolve one status bar/ navigation bar assumption
+                return;
+            }
             StatusBarManagerService.this.topAppWindowChanged(menuVisible);
         }
 
         @Override
-        public void setSystemUiVisibility(int vis, int fullscreenStackVis, int dockedStackVis,
-                int mask,
-                Rect fullscreenBounds, Rect dockedBounds, String cause) {
+        public void setSystemUiVisibility(int displayId, int vis, int fullscreenStackVis,
+                int dockedStackVis, int mask, Rect fullscreenBounds, Rect dockedBounds,
+                String cause) {
+            if (displayId != Display.DEFAULT_DISPLAY) {
+                // TODO (b/117478341): Resolve one status bar/ navigation bar assumption
+                return;
+            }
             StatusBarManagerService.this.setSystemUiVisibility(vis, fullscreenStackVis,
                     dockedStackVis, mask, fullscreenBounds, dockedBounds, cause);
         }
@@ -259,8 +268,13 @@
             }
         }
 
-        public void appTransitionFinished() {
+        @Override
+        public void appTransitionFinished(int displayId) {
             enforceStatusBarService();
+            if (displayId != Display.DEFAULT_DISPLAY) {
+                // TODO (b/117478341): Resolve one status bar/ navigation bar assumption
+                return;
+            }
             if (mBar != null) {
                 try {
                     mBar.appTransitionFinished();
@@ -358,7 +372,11 @@
         }
 
         @Override
-        public void setWindowState(int window, int state) {
+        public void setWindowState(int displayId, int window, int state) {
+            if (displayId != Display.DEFAULT_DISPLAY) {
+                // TODO (b/117478341): Resolve one status bar/ navigation bar assumption
+                return;
+            }
             if (mBar != null) {
                 try {
                     mBar.setWindowState(window, state);
@@ -367,7 +385,11 @@
         }
 
         @Override
-        public void appTransitionPending() {
+        public void appTransitionPending(int displayId) {
+            if (displayId != Display.DEFAULT_DISPLAY) {
+                // TODO (b/117478341): Resolve one status bar/ navigation bar assumption
+                return;
+            }
             if (mBar != null) {
                 try {
                     mBar.appTransitionPending();
@@ -376,7 +398,11 @@
         }
 
         @Override
-        public void appTransitionCancelled() {
+        public void appTransitionCancelled(int displayId) {
+            if (displayId != Display.DEFAULT_DISPLAY) {
+                // TODO (b/117478341): Resolve one status bar/ navigation bar assumption
+                return;
+            }
             if (mBar != null) {
                 try {
                     mBar.appTransitionCancelled();
@@ -385,8 +411,12 @@
         }
 
         @Override
-        public void appTransitionStarting(long statusBarAnimationsStartTime,
+        public void appTransitionStarting(int displayId, long statusBarAnimationsStartTime,
                 long statusBarAnimationsDuration) {
+            if (displayId != Display.DEFAULT_DISPLAY) {
+                // TODO (b/117478341): Resolve one status bar/ navigation bar assumption
+                return;
+            }
             if (mBar != null) {
                 try {
                     mBar.appTransitionStarting(
diff --git a/services/core/java/com/android/server/wm/ActivityRecord.java b/services/core/java/com/android/server/wm/ActivityRecord.java
index c43e64e..5e92b9e 100644
--- a/services/core/java/com/android/server/wm/ActivityRecord.java
+++ b/services/core/java/com/android/server/wm/ActivityRecord.java
@@ -2354,7 +2354,7 @@
         // bounds would end up too small.
         outBounds.set(0, 0, maxActivityWidth + appBounds.left, maxActivityHeight + appBounds.top);
 
-        if (service.mWindowManager.getNavBarPosition() == NAV_BAR_LEFT) {
+        if (service.mWindowManager.getNavBarPosition(getDisplayId()) == NAV_BAR_LEFT) {
             // Position the activity frame on the opposite side of the nav bar.
             outBounds.left = appBounds.right - maxActivityWidth;
             outBounds.right = appBounds.right;
diff --git a/services/core/java/com/android/server/wm/AppTransitionController.java b/services/core/java/com/android/server/wm/AppTransitionController.java
index e65f3b4..32a6f74 100644
--- a/services/core/java/com/android/server/wm/AppTransitionController.java
+++ b/services/core/java/com/android/server/wm/AppTransitionController.java
@@ -96,14 +96,15 @@
         Trace.traceBegin(Trace.TRACE_TAG_WINDOW_MANAGER, "AppTransitionReady");
 
         if (DEBUG_APP_TRANSITIONS) Slog.v(TAG, "**** GOOD TO GO");
-        int transit = mDisplayContent.mAppTransition.getAppTransition();
+        final AppTransition appTransition = mDisplayContent.mAppTransition;
+        int transit = appTransition.getAppTransition();
         if (mDisplayContent.mSkipAppTransitionAnimation && !isKeyguardGoingAwayTransit(transit)) {
             transit = WindowManager.TRANSIT_UNSET;
         }
         mDisplayContent.mSkipAppTransitionAnimation = false;
         mDisplayContent.mNoAnimationNotifyOnTransitionFinished.clear();
 
-        mDisplayContent.mAppTransition.removeAppTransitionTimeoutCallbacks();
+        appTransition.removeAppTransitionTimeoutCallbacks();
 
         mDisplayContent.mWallpaperMayChange = false;
 
@@ -141,7 +142,7 @@
         // done behind a dream window.
         final ArraySet<Integer> activityTypes = collectActivityTypes(mDisplayContent.mOpeningApps,
                 mDisplayContent.mClosingApps);
-        final boolean allowAnimations = mService.mPolicy.allowAppAnimationsLw();
+        final boolean allowAnimations = mDisplayContent.getDisplayPolicy().allowAppAnimationsLw();
         final AppWindowToken animLpToken = allowAnimations
                 ? findAnimLayoutParamsToken(transit, activityTypes)
                 : null;
@@ -165,15 +166,15 @@
             handleClosingApps(transit, animLp, voiceInteraction);
             handleOpeningApps(transit, animLp, voiceInteraction);
 
-            mDisplayContent.mAppTransition.setLastAppTransition(transit, topOpeningApp,
+            appTransition.setLastAppTransition(transit, topOpeningApp,
                     topClosingApp);
 
-            final int flags = mDisplayContent.mAppTransition.getTransitFlags();
-            layoutRedo = mDisplayContent.mAppTransition.goodToGo(transit, topOpeningApp,
+            final int flags = appTransition.getTransitFlags();
+            layoutRedo = appTransition.goodToGo(transit, topOpeningApp,
                     topClosingApp, mDisplayContent.mOpeningApps, mDisplayContent.mClosingApps);
             handleNonAppWindowsInTransition(transit, flags);
-            mDisplayContent.mAppTransition.postAnimationCallback();
-            mDisplayContent.mAppTransition.clear();
+            appTransition.postAnimationCallback();
+            appTransition.clear();
         } finally {
             mService.mSurfaceAnimationRunner.continueStartingAnimations();
         }
@@ -254,8 +255,8 @@
     }
 
     /**
-     * @return The set of {@link WindowConfiguration.ActivityType}s contained in the set of apps in
-     *         {@code array1} and {@code array2}.
+     * @return The set of {@link android.app.WindowConfiguration.ActivityType}s contained in the set
+     *         of apps in {@code array1} and {@code array2}.
      */
     private static ArraySet<Integer> collectActivityTypes(ArraySet<AppWindowToken> array1,
             ArraySet<AppWindowToken> array2) {
diff --git a/services/core/java/com/android/server/policy/BarController.java b/services/core/java/com/android/server/wm/BarController.java
similarity index 90%
rename from services/core/java/com/android/server/policy/BarController.java
rename to services/core/java/com/android/server/wm/BarController.java
index 14c985c..a335fa2 100644
--- a/services/core/java/com/android/server/policy/BarController.java
+++ b/services/core/java/com/android/server/wm/BarController.java
@@ -1,5 +1,5 @@
 /*
- * Copyright (C) 2013 The Android Open Source Project
+ * Copyright (C) 2018 The Android Open Source Project
  *
  * Licensed under the Apache License, Version 2.0 (the "License");
  * you may not use this file except in compliance with the License.
@@ -14,7 +14,7 @@
  * limitations under the License.
  */
 
-package com.android.server.policy;
+package com.android.server.wm;
 
 import static com.android.server.wm.BarControllerProto.STATE;
 import static com.android.server.wm.BarControllerProto.TRANSIENT_STATE;
@@ -30,7 +30,7 @@
 import android.view.WindowManager;
 
 import com.android.server.LocalServices;
-import com.android.server.policy.WindowManagerPolicy.WindowState;
+import com.android.server.UiThread;
 import com.android.server.statusbar.StatusBarManagerInternal;
 
 import java.io.PrintWriter;
@@ -59,7 +59,7 @@
     private final int mTranslucentWmFlag;
     protected final Handler mHandler;
     private final Object mServiceAquireLock = new Object();
-    protected StatusBarManagerInternal mStatusBarInternal;
+    private StatusBarManagerInternal mStatusBarInternal;
 
     protected WindowState mWin;
     private int mState = StatusBarManager.WINDOW_STATE_SHOWING;
@@ -73,7 +73,7 @@
 
     private OnBarVisibilityChangedListener mVisibilityChangeListener;
 
-    public BarController(String tag, int transientFlag, int unhideFlag, int translucentFlag,
+    BarController(String tag, int transientFlag, int unhideFlag, int translucentFlag,
             int statusBarManagerId, int translucentWmFlag, int transparentFlag) {
         mTag = "BarController." + tag;
         mTransientFlag = transientFlag;
@@ -85,7 +85,7 @@
         mHandler = new BarHandler();
     }
 
-    public void setWindow(WindowState win) {
+    void setWindow(WindowState win) {
         mWin = win;
     }
 
@@ -94,11 +94,11 @@
      *
      * This is used to determine if letterboxes interfere with the display of such content.
      */
-    public void setContentFrame(Rect frame) {
+    void setContentFrame(Rect frame) {
         mContentFrame.set(frame);
     }
 
-    public void setShowTransparent(boolean transparent) {
+    void setShowTransparent(boolean transparent) {
         if (transparent != mShowTransparent) {
             mShowTransparent = transparent;
             mSetUnHideFlagWhenNextTransparent = transparent;
@@ -106,27 +106,27 @@
         }
     }
 
-    public void showTransient() {
+    void showTransient() {
         if (mWin != null) {
             setTransientBarState(TRANSIENT_BAR_SHOW_REQUESTED);
         }
     }
 
-    public boolean isTransientShowing() {
+    boolean isTransientShowing() {
         return mTransientBarState == TRANSIENT_BAR_SHOWING;
     }
 
-    public boolean isTransientShowRequested() {
+    boolean isTransientShowRequested() {
         return mTransientBarState == TRANSIENT_BAR_SHOW_REQUESTED;
     }
 
-    public boolean wasRecentlyTranslucent() {
+    boolean wasRecentlyTranslucent() {
         return (SystemClock.uptimeMillis() - mLastTranslucent) < TRANSLUCENT_ANIMATION_DELAY_MS;
     }
 
-    public void adjustSystemUiVisibilityLw(int oldVis, int vis) {
-        if (mWin != null && mTransientBarState == TRANSIENT_BAR_SHOWING &&
-                (vis & mTransientFlag) == 0) {
+    void adjustSystemUiVisibilityLw(int oldVis, int vis) {
+        if (mWin != null && mTransientBarState == TRANSIENT_BAR_SHOWING
+                && (vis & mTransientFlag) == 0) {
             // sysui requests hide
             setTransientBarState(TRANSIENT_BAR_HIDING);
             setBarShowingLw(false);
@@ -136,7 +136,7 @@
         }
     }
 
-    public int applyTranslucentFlagLw(WindowState win, int vis, int oldVis) {
+    int applyTranslucentFlagLw(WindowState win, int vis, int oldVis) {
         if (mWin != null) {
             if (win != null && (win.getAttrs().privateFlags
                     & WindowManager.LayoutParams.PRIVATE_FLAG_INHERIT_TRANSLUCENT_DECOR) == 0) {
@@ -164,7 +164,7 @@
         return win == null || !win.isLetterboxedOverlappingWith(mContentFrame);
     }
 
-    public boolean setBarShowingLw(final boolean show) {
+    boolean setBarShowingLw(final boolean show) {
         if (mWin == null) return false;
         if (show && mTransientBarState == TRANSIENT_BAR_HIDING) {
             mPendingShow = true;
@@ -227,7 +227,7 @@
                 public void run() {
                     StatusBarManagerInternal statusbar = getStatusBarInternal();
                     if (statusbar != null) {
-                        statusbar.setWindowState(mStatusBarManagerId, state);
+                        statusbar.setWindowState(mWin.getDisplayId(), mStatusBarManagerId, state);
                     }
                 }
             });
@@ -236,7 +236,7 @@
         return false;
     }
 
-    public boolean checkHiddenLw() {
+    boolean checkHiddenLw() {
         if (mWin != null && mWin.isDrawnLw()) {
             if (!mWin.isVisibleLw() && !mWin.isAnimatingLw()) {
                 updateStateLw(StatusBarManager.WINDOW_STATE_HIDDEN);
@@ -254,7 +254,7 @@
         return false;
     }
 
-    public boolean checkShowTransientBarLw() {
+    boolean checkShowTransientBarLw() {
         if (mTransientBarState == TRANSIENT_BAR_SHOWING) {
             if (DEBUG) Slog.d(mTag, "Not showing transient bar, already shown");
             return false;
@@ -272,7 +272,7 @@
         }
     }
 
-    public int updateVisibilityLw(boolean transientAllowed, int oldVis, int vis) {
+    int updateVisibilityLw(boolean transientAllowed, int oldVis, int vis) {
         if (mWin == null) return vis;
         if (isTransientShowing() || isTransientShowRequested()) { // transient bar requested
             if (transientAllowed) {
@@ -296,8 +296,8 @@
             vis |= mTransientFlag;  // ignore clear requests until transition completes
             vis &= ~View.SYSTEM_UI_FLAG_LOW_PROFILE;  // never show transient bars in low profile
         }
-        if ((vis & mTranslucentFlag) != 0 || (oldVis & mTranslucentFlag) != 0 ||
-                ((vis | oldVis) & mTransparentFlag) != 0) {
+        if ((vis & mTranslucentFlag) != 0 || (oldVis & mTranslucentFlag) != 0
+                || ((vis | oldVis) & mTransparentFlag) != 0) {
             mLastTranslucent = SystemClock.uptimeMillis();
         }
         return vis;
@@ -330,14 +330,14 @@
         throw new IllegalArgumentException("Unknown state " + state);
     }
 
-    public void writeToProto(ProtoOutputStream proto, long fieldId) {
+    void writeToProto(ProtoOutputStream proto, long fieldId) {
         final long token = proto.start(fieldId);
         proto.write(STATE, mState);
         proto.write(TRANSIENT_STATE, mTransientBarState);
         proto.end(token);
     }
 
-    public void dump(PrintWriter pw, String prefix) {
+    void dump(PrintWriter pw, String prefix) {
         if (mWin != null) {
             pw.print(prefix); pw.println(mTag);
             pw.print(prefix); pw.print("  "); pw.print("mState"); pw.print('=');
@@ -349,6 +349,10 @@
     }
 
     private class BarHandler extends Handler {
+        BarHandler() {
+            super(UiThread.getHandler().getLooper());
+        }
+
         @Override
         public void handleMessage(Message msg) {
             switch (msg.what) {
diff --git a/services/core/java/com/android/server/wm/DisplayContent.java b/services/core/java/com/android/server/wm/DisplayContent.java
index 2f7956e..886b2ff 100644
--- a/services/core/java/com/android/server/wm/DisplayContent.java
+++ b/services/core/java/com/android/server/wm/DisplayContent.java
@@ -156,6 +156,7 @@
 import android.view.SurfaceControl;
 import android.view.SurfaceControl.Transaction;
 import android.view.SurfaceSession;
+import android.view.View;
 import android.view.WindowManager;
 import android.view.WindowManagerPolicyConstants.PointerEventListener;
 
@@ -182,9 +183,6 @@
 /**
  * Utility class for keeping track of the WindowStates and other pertinent contents of a
  * particular Display.
- *
- * IMPORTANT: No method from this class should ever be used without holding
- * WindowManagerService.mWindowMap.
  */
 class DisplayContent extends WindowContainer<DisplayContent.DisplayChildWindowContainer>
         implements WindowManagerPolicy.DisplayContentInfo {
@@ -289,7 +287,8 @@
      * @see WindowManagerService#createWatermarkInTransaction()
      */
     final DisplayMetrics mRealDisplayMetrics = new DisplayMetrics();
-    /** @see #computeCompatSmallestWidth(boolean, int, int, int, int) */
+
+    /** @see #computeCompatSmallestWidth(boolean, int, int, int, DisplayCutout) */
     private final DisplayMetrics mTmpDisplayMetrics = new DisplayMetrics();
 
     /**
@@ -508,6 +507,11 @@
 
     private final PointerEventDispatcher mPointerEventDispatcher;
 
+    // Last systemUiVisibility we received from status bar.
+    private int mLastStatusBarVisibility = 0;
+    // Last systemUiVisibility we dispatched to windows.
+    private int mLastDispatchedSystemUiVisibility = 0;
+
     private final Consumer<WindowState> mUpdateWindowsForAnimator = w -> {
         WindowStateAnimator winAnimator = w.mWinAnimator;
         final AppWindowToken atoken = w.mAppToken;
@@ -649,7 +653,7 @@
                 w.mLayoutNeeded = false;
                 w.prelayout();
                 final boolean firstLayout = !w.isLaidOut();
-                mService.mPolicy.layoutWindowLw(w, null, mDisplayFrames);
+                getDisplayPolicy().layoutWindowLw(w, null, mDisplayFrames);
                 w.mLayoutSeq = mLayoutSeq;
 
                 // If this is the first layout, we need to initialize the last inset values as
@@ -688,7 +692,7 @@
                 }
                 w.mLayoutNeeded = false;
                 w.prelayout();
-                mService.mPolicy.layoutWindowLw(w, w.getParentWindow(), mDisplayFrames);
+                getDisplayPolicy().layoutWindowLw(w, w.getParentWindow(), mDisplayFrames);
                 w.mLayoutSeq = mLayoutSeq;
                 if (DEBUG_LAYOUT) Slog.v(TAG, " LAYOUT: mFrame=" + w.getFrameLw()
                         + " mContainingFrame=" + w.getContainingFrame()
@@ -708,7 +712,7 @@
     };
 
     private final Consumer<WindowState> mApplyPostLayoutPolicy =
-            w -> mService.mPolicy.applyPostLayoutPolicyLw(w, w.mAttrs, w.getParentWindow(),
+            w -> getDisplayPolicy().applyPostLayoutPolicyLw(w, w.mAttrs, w.getParentWindow(),
                     mInputMethodTarget);
 
     private final Consumer<WindowState> mApplySurfaceChangesTransaction = w -> {
@@ -838,15 +842,6 @@
         mDisplayFrames = new DisplayFrames(mDisplayId, mDisplayInfo,
                 calculateDisplayCutoutForRotation(mDisplayInfo.rotation));
         initializeDisplayBaseInfo();
-        mDisplayPolicy = new DisplayPolicy(service);
-        mDisplayRotation = new DisplayRotation(service, this);
-        if (isDefaultDisplay) {
-            // The policy may be invoked right after here, so it requires the necessary default
-            // fields of this display content.
-            mService.mPolicy.setDefaultDisplay(this);
-        }
-        mDividerControllerLocked = new DockedStackDividerController(service, this);
-        mPinnedStackControllerLocked = new PinnedStackController(service, this);
 
         mAppTransition = new AppTransition(service.mContext, service, this);
         mAppTransition.registerListenerLocked(service.mActivityManagerAppTransitionNotifier);
@@ -857,6 +852,30 @@
         mBoundsAnimationController = new BoundsAnimationController(service.mContext,
                 mAppTransition, SurfaceAnimationThread.getHandler(), animationHandler);
 
+        if (mService.mInputManager != null) {
+            final InputChannel inputChannel = mService.mInputManager.monitorInput("Display "
+                    + mDisplayId, mDisplayId);
+            mPointerEventDispatcher = inputChannel != null
+                    ? new PointerEventDispatcher(inputChannel) : null;
+        } else {
+            mPointerEventDispatcher = null;
+        }
+        mDisplayPolicy = new DisplayPolicy(service, this);
+        mDisplayRotation = new DisplayRotation(service, this);
+        if (isDefaultDisplay) {
+            // The policy may be invoked right after here, so it requires the necessary default
+            // fields of this display content.
+            mService.mPolicy.setDefaultDisplay(this);
+        }
+        if (mService.mDisplayReady) {
+            mDisplayPolicy.onConfigurationChanged();
+        }
+        if (mService.mSystemReady) {
+            mDisplayPolicy.systemReady();
+        }
+        mDividerControllerLocked = new DockedStackDividerController(service, this);
+        mPinnedStackControllerLocked = new PinnedStackController(service, this);
+
         // We use this as our arbitrary surface size for buffer-less parents
         // that don't impose cropping on their children. It may need to be larger
         // than the display size because fullscreen windows can be shifted offscreen
@@ -895,15 +914,6 @@
 
         mService.mAnimator.addDisplayLocked(mDisplayId);
         mInputMonitor = new InputMonitor(service, mDisplayId);
-
-        if (mService.mInputManager != null) {
-            final InputChannel inputChannel = mService.mInputManager.monitorInput("Display "
-                    + mDisplayId, mDisplayId);
-            mPointerEventDispatcher = inputChannel != null
-                    ? new PointerEventDispatcher(inputChannel) : null;
-        } else {
-            mPointerEventDispatcher = null;
-        }
     }
 
     boolean isReady() {
@@ -1223,7 +1233,7 @@
         if (DEBUG_ORIENTATION) Slog.v(TAG_WM, "Computed rotation=" + rotation + " for display id="
                 + mDisplayId + " based on lastOrientation=" + lastOrientation
                 + " and oldRotation=" + oldRotation);
-        boolean mayRotateSeamlessly = mService.mPolicy.shouldRotateSeamlessly(mDisplayRotation,
+        boolean mayRotateSeamlessly = mDisplayPolicy.shouldRotateSeamlessly(mDisplayRotation,
                 oldRotation, rotation);
 
         if (mayRotateSeamlessly) {
@@ -1286,7 +1296,7 @@
 
         setLayoutNeeded();
         final int[] anim = new int[2];
-        mService.mPolicy.selectRotationAnimationLw(anim);
+        mDisplayPolicy.selectRotationAnimationLw(anim);
 
         if (!rotateSeamlessly) {
             mService.startFreezingDisplayLocked(anim[0], anim[1], this);
@@ -1445,10 +1455,10 @@
         final WmDisplayCutout wmDisplayCutout = calculateDisplayCutoutForRotation(mRotation);
         final DisplayCutout displayCutout = wmDisplayCutout.getDisplayCutout();
 
-        final int appWidth = mService.mPolicy.getNonDecorDisplayWidth(dw, dh, mRotation, uiMode,
-                mDisplayId, displayCutout);
-        final int appHeight = mService.mPolicy.getNonDecorDisplayHeight(dw, dh, mRotation, uiMode,
-                mDisplayId, displayCutout);
+        final int appWidth = mDisplayPolicy.getNonDecorDisplayWidth(dw, dh, mRotation, uiMode,
+                displayCutout);
+        final int appHeight = mDisplayPolicy.getNonDecorDisplayHeight(dw, dh, mRotation, uiMode,
+                displayCutout);
         mDisplayInfo.rotation = mRotation;
         mDisplayInfo.logicalWidth = dw;
         mDisplayInfo.logicalHeight = dh;
@@ -1527,13 +1537,13 @@
 
         final float density = mDisplayMetrics.density;
         config.screenWidthDp =
-                (int)(mService.mPolicy.getConfigDisplayWidth(dw, dh, displayInfo.rotation,
-                        config.uiMode, mDisplayId, displayInfo.displayCutout) / density);
+                (int)(mDisplayPolicy.getConfigDisplayWidth(dw, dh, displayInfo.rotation,
+                        config.uiMode, displayInfo.displayCutout) / density);
         config.screenHeightDp =
-                (int)(mService.mPolicy.getConfigDisplayHeight(dw, dh, displayInfo.rotation,
-                        config.uiMode, mDisplayId, displayInfo.displayCutout) / density);
+                (int)(mDisplayPolicy.getConfigDisplayHeight(dw, dh, displayInfo.rotation,
+                        config.uiMode, displayInfo.displayCutout) / density);
 
-        mService.mPolicy.getNonDecorInsetsLw(displayInfo.rotation, dw, dh,
+        mDisplayPolicy.getNonDecorInsetsLw(displayInfo.rotation, dw, dh,
                 displayInfo.displayCutout, mTmpRect);
         final int leftInset = mTmpRect.left;
         final int topInset = mTmpRect.top;
@@ -1544,8 +1554,8 @@
         final boolean rotated = (displayInfo.rotation == Surface.ROTATION_90
                 || displayInfo.rotation == Surface.ROTATION_270);
 
-        computeSizeRangesAndScreenLayout(displayInfo, mDisplayId, rotated, config.uiMode, dw, dh,
-                density, config);
+        computeSizeRangesAndScreenLayout(displayInfo, rotated, config.uiMode, dw, dh, density,
+                config);
 
         config.screenLayout = (config.screenLayout & ~Configuration.SCREENLAYOUT_ROUND_MASK)
                 | ((displayInfo.flags & Display.FLAG_ROUND) != 0
@@ -1555,7 +1565,7 @@
         config.compatScreenWidthDp = (int)(config.screenWidthDp / mCompatibleScreenScale);
         config.compatScreenHeightDp = (int)(config.screenHeightDp / mCompatibleScreenScale);
         config.compatSmallestScreenWidthDp = computeCompatSmallestWidth(rotated, config.uiMode, dw,
-                dh, displayInfo.displayCutout, mDisplayId);
+                dh, displayInfo.displayCutout);
         config.densityDpi = displayInfo.logicalDensityDpi;
 
         config.colorMode =
@@ -1624,6 +1634,8 @@
             mService.mH.sendEmptyMessage(WindowManagerService.H.REPORT_HARD_KEYBOARD_STATUS_CHANGE);
         }
 
+        mDisplayPolicy.updateConfigurationDependentBehaviors();
+
         // Let the policy update hidden states.
         config.keyboardHidden = Configuration.KEYBOARDHIDDEN_NO;
         config.hardKeyboardHidden = Configuration.HARDKEYBOARDHIDDEN_NO;
@@ -1632,7 +1644,7 @@
     }
 
     private int computeCompatSmallestWidth(boolean rotated, int uiMode, int dw, int dh,
-            DisplayCutout displayCutout, int displayId) {
+            DisplayCutout displayCutout) {
         mTmpDisplayMetrics.setTo(mDisplayMetrics);
         final DisplayMetrics tmpDm = mTmpDisplayMetrics;
         final int unrotDw, unrotDh;
@@ -1644,22 +1656,22 @@
             unrotDh = dh;
         }
         int sw = reduceCompatConfigWidthSize(0, Surface.ROTATION_0, uiMode, tmpDm, unrotDw, unrotDh,
-                displayCutout, displayId);
+                displayCutout);
         sw = reduceCompatConfigWidthSize(sw, Surface.ROTATION_90, uiMode, tmpDm, unrotDh, unrotDw,
-                displayCutout, displayId);
+                displayCutout);
         sw = reduceCompatConfigWidthSize(sw, Surface.ROTATION_180, uiMode, tmpDm, unrotDw, unrotDh,
-                displayCutout, displayId);
+                displayCutout);
         sw = reduceCompatConfigWidthSize(sw, Surface.ROTATION_270, uiMode, tmpDm, unrotDh, unrotDw,
-                displayCutout, displayId);
+                displayCutout);
         return sw;
     }
 
     private int reduceCompatConfigWidthSize(int curSize, int rotation, int uiMode,
-            DisplayMetrics dm, int dw, int dh, DisplayCutout displayCutout, int displayId) {
-        dm.noncompatWidthPixels = mService.mPolicy.getNonDecorDisplayWidth(dw, dh, rotation, uiMode,
-                displayId, displayCutout);
-        dm.noncompatHeightPixels = mService.mPolicy.getNonDecorDisplayHeight(dw, dh, rotation,
-                uiMode, displayId, displayCutout);
+            DisplayMetrics dm, int dw, int dh, DisplayCutout displayCutout) {
+        dm.noncompatWidthPixels = mDisplayPolicy.getNonDecorDisplayWidth(dw, dh, rotation, uiMode,
+                displayCutout);
+        dm.noncompatHeightPixels = mDisplayPolicy.getNonDecorDisplayHeight(dw, dh, rotation, uiMode,
+                displayCutout);
         float scale = CompatibilityInfo.computeCompatibleScaling(dm, null);
         int size = (int)(((dm.noncompatWidthPixels / scale) / dm.density) + .5f);
         if (curSize == 0 || size < curSize) {
@@ -1668,8 +1680,8 @@
         return curSize;
     }
 
-    private void computeSizeRangesAndScreenLayout(DisplayInfo displayInfo, int displayId,
-            boolean rotated, int uiMode, int dw, int dh, float density, Configuration outConfig) {
+    private void computeSizeRangesAndScreenLayout(DisplayInfo displayInfo, boolean rotated,
+            int uiMode, int dw, int dh, float density, Configuration outConfig) {
 
         // We need to determine the smallest width that will occur under normal
         // operation.  To this, start with the base screen size and compute the
@@ -1687,34 +1699,28 @@
         displayInfo.smallestNominalAppHeight = 1<<30;
         displayInfo.largestNominalAppWidth = 0;
         displayInfo.largestNominalAppHeight = 0;
-        adjustDisplaySizeRanges(displayInfo, displayId, Surface.ROTATION_0, uiMode, unrotDw,
-                unrotDh);
-        adjustDisplaySizeRanges(displayInfo, displayId, Surface.ROTATION_90, uiMode, unrotDh,
-                unrotDw);
-        adjustDisplaySizeRanges(displayInfo, displayId, Surface.ROTATION_180, uiMode, unrotDw,
-                unrotDh);
-        adjustDisplaySizeRanges(displayInfo, displayId, Surface.ROTATION_270, uiMode, unrotDh,
-                unrotDw);
+        adjustDisplaySizeRanges(displayInfo, Surface.ROTATION_0, uiMode, unrotDw, unrotDh);
+        adjustDisplaySizeRanges(displayInfo, Surface.ROTATION_90, uiMode, unrotDh, unrotDw);
+        adjustDisplaySizeRanges(displayInfo, Surface.ROTATION_180, uiMode, unrotDw, unrotDh);
+        adjustDisplaySizeRanges(displayInfo, Surface.ROTATION_270, uiMode, unrotDh, unrotDw);
         int sl = Configuration.resetScreenLayout(outConfig.screenLayout);
         sl = reduceConfigLayout(sl, Surface.ROTATION_0, density, unrotDw, unrotDh, uiMode,
-                displayInfo.displayCutout, displayId);
+                displayInfo.displayCutout);
         sl = reduceConfigLayout(sl, Surface.ROTATION_90, density, unrotDh, unrotDw, uiMode,
-                displayInfo.displayCutout, displayId);
+                displayInfo.displayCutout);
         sl = reduceConfigLayout(sl, Surface.ROTATION_180, density, unrotDw, unrotDh, uiMode,
-                displayInfo.displayCutout, displayId);
+                displayInfo.displayCutout);
         sl = reduceConfigLayout(sl, Surface.ROTATION_270, density, unrotDh, unrotDw, uiMode,
-                displayInfo.displayCutout, displayId);
+                displayInfo.displayCutout);
         outConfig.smallestScreenWidthDp = (int)(displayInfo.smallestNominalAppWidth / density);
         outConfig.screenLayout = sl;
     }
 
     private int reduceConfigLayout(int curLayout, int rotation, float density, int dw, int dh,
-            int uiMode, DisplayCutout displayCutout, int displayId) {
+            int uiMode, DisplayCutout displayCutout) {
         // Get the app screen size at this rotation.
-        int w = mService.mPolicy.getNonDecorDisplayWidth(dw, dh, rotation, uiMode, displayId,
-                displayCutout);
-        int h = mService.mPolicy.getNonDecorDisplayHeight(dw, dh, rotation, uiMode, displayId,
-                displayCutout);
+        int w = mDisplayPolicy.getNonDecorDisplayWidth(dw, dh, rotation, uiMode, displayCutout);
+        int h = mDisplayPolicy.getNonDecorDisplayHeight(dw, dh, rotation, uiMode, displayCutout);
 
         // Compute the screen layout size class for this rotation.
         int longSize = w;
@@ -1729,20 +1735,20 @@
         return Configuration.reduceScreenLayout(curLayout, longSize, shortSize);
     }
 
-    private void adjustDisplaySizeRanges(DisplayInfo displayInfo, int displayId, int rotation,
+    private void adjustDisplaySizeRanges(DisplayInfo displayInfo, int rotation,
             int uiMode, int dw, int dh) {
         final DisplayCutout displayCutout = calculateDisplayCutoutForRotation(
                 rotation).getDisplayCutout();
-        final int width = mService.mPolicy.getConfigDisplayWidth(dw, dh, rotation, uiMode,
-                displayId, displayCutout);
+        final int width = mDisplayPolicy.getConfigDisplayWidth(dw, dh, rotation, uiMode,
+                displayCutout);
         if (width < displayInfo.smallestNominalAppWidth) {
             displayInfo.smallestNominalAppWidth = width;
         }
         if (width > displayInfo.largestNominalAppWidth) {
             displayInfo.largestNominalAppWidth = width;
         }
-        final int height = mService.mPolicy.getConfigDisplayHeight(dw, dh, rotation, uiMode,
-                displayId, displayCutout);
+        final int height = mDisplayPolicy.getConfigDisplayHeight(dw, dh, rotation, uiMode,
+                displayCutout);
         if (height < displayInfo.smallestNominalAppHeight) {
             displayInfo.smallestNominalAppHeight = height;
         }
@@ -1887,6 +1893,9 @@
     @Override
     public void onConfigurationChanged(Configuration newParentConfig) {
         super.onConfigurationChanged(newParentConfig);
+        if (mDisplayPolicy != null) {
+            mDisplayPolicy.onConfigurationChanged();
+        }
 
         // If there was no pinned stack, we still need to notify the controller of the display info
         // update as a result of the config change.
@@ -2383,7 +2392,7 @@
             mDisplayReady = false;
             mRemovingDisplay = false;
         }
-
+        mDisplayPolicy.onDisplayRemoved();
         mInputMonitor.onRemoved();
         mService.mWindowPlacerLocked.requestTraversal();
     }
@@ -2659,6 +2668,10 @@
             }
         }
         pw.print("  mFocusedApp="); pw.println(mFocusedApp);
+        if (mLastStatusBarVisibility != 0) {
+            pw.print("  mLastStatusBarVisibility=0x");
+            pw.println(Integer.toHexString(mLastStatusBarVisibility));
+        }
 
         pw.println();
         mWallpaperController.dump(pw, "  ");
@@ -2852,9 +2865,7 @@
             }
         }
 
-        // System UI is only shown on the default display.
-        int focusChanged = isDefaultDisplay
-                ? mService.mPolicy.focusChangedLw(oldFocus, newFocus) : 0;
+        int focusChanged = getDisplayPolicy().focusChangedLw(oldFocus, newFocus);
 
         if (imWindowChanged && oldFocus != mInputMethodWindow) {
             // Focus of the input method window changed. Perform layout if needed.
@@ -3321,6 +3332,31 @@
         return win != null;
     }
 
+    void statusBarVisibilityChanged(int visibility) {
+        mLastStatusBarVisibility = visibility;
+        visibility = getDisplayPolicy().adjustSystemUiVisibilityLw(visibility);
+        updateStatusBarVisibilityLocked(visibility);
+    }
+
+    private boolean updateStatusBarVisibilityLocked(int visibility) {
+        if (mLastDispatchedSystemUiVisibility == visibility) {
+            return false;
+        }
+        final int globalDiff = (visibility ^ mLastDispatchedSystemUiVisibility)
+                // We are only interested in differences of one of the
+                // clearable flags...
+                & View.SYSTEM_UI_CLEARABLE_FLAGS
+                // ...if it has actually been cleared.
+                & ~visibility;
+
+        mLastDispatchedSystemUiVisibility = visibility;
+        if (isDefaultDisplay) {
+            mService.mInputManager.setSystemUiVisibility(visibility);
+        }
+        updateSystemUiVisibility(visibility, globalDiff);
+        return true;
+    }
+
     void updateSystemUiVisibility(int visibility, int globalDiff) {
         forAllWindows(w -> {
             try {
@@ -3341,6 +3377,13 @@
         }, true /* traverseTopToBottom */);
     }
 
+    void reevaluateStatusBarVisibility() {
+        int visibility = getDisplayPolicy().adjustSystemUiVisibilityLw(mLastStatusBarVisibility);
+        if (updateStatusBarVisibilityLocked(visibility)) {
+            mService.mWindowPlacerLocked.requestTraversal();
+        }
+    }
+
     void onWindowFreezeTimeout() {
         Slog.w(TAG_WM, "Window freeze timeout expired.");
         mService.mWindowsFreezingScreen = WINDOWS_FREEZING_SCREENS_TIMEOUT;
@@ -3372,9 +3415,6 @@
 
     // TODO: Super crazy long method that should be broken down...
     void applySurfaceChangesTransaction(boolean recoveringMemory) {
-
-        final int dw = mDisplayInfo.logicalWidth;
-        final int dh = mDisplayInfo.logicalHeight;
         final WindowSurfacePlacer surfacePlacer = mService.mWindowPlacerLocked;
 
         mTmpUpdateAllDrawn.clear();
@@ -3417,13 +3457,11 @@
             // FIRST AND ONE HALF LOOP: Make WindowManagerPolicy think it is animating.
             pendingLayoutChanges = 0;
 
-            if (isDefaultDisplay) {
-                mService.mPolicy.beginPostLayoutPolicyLw(dw, dh);
-                forAllWindows(mApplyPostLayoutPolicy, true /* traverseTopToBottom */);
-                pendingLayoutChanges |= mService.mPolicy.finishPostLayoutPolicyLw();
-                if (DEBUG_LAYOUT_REPEATS) surfacePlacer.debugLayoutRepeats(
-                        "after finishPostLayoutPolicyLw", pendingLayoutChanges);
-            }
+            mDisplayPolicy.beginPostLayoutPolicyLw();
+            forAllWindows(mApplyPostLayoutPolicy, true /* traverseTopToBottom */);
+            pendingLayoutChanges |= mDisplayPolicy.finishPostLayoutPolicyLw();
+            if (DEBUG_LAYOUT_REPEATS) surfacePlacer.debugLayoutRepeats(
+                    "after finishPostLayoutPolicyLw", pendingLayoutChanges);
         } while (pendingLayoutChanges != 0);
 
         mTmpApplySurfaceChangesTransactionState.reset();
@@ -3513,12 +3551,7 @@
         // TODO: Not sure if we really need to set the rotation here since we are updating from the
         // display info above...
         mDisplayFrames.mRotation = mRotation;
-        mService.mPolicy.beginLayoutLw(mDisplayFrames, getConfiguration().uiMode);
-        if (isDefaultDisplay) {
-            // Not needed on non-default displays.
-            mService.mSystemDecorLayer = mService.mPolicy.getSystemDecorLayerLw();
-            mService.mScreenRect.set(0, 0, dw, dh);
-        }
+        mDisplayPolicy.beginLayoutLw(mDisplayFrames, getConfiguration().uiMode);
 
         int seq = mLayoutSeq + 1;
         if (seq < 0) seq = 0;
@@ -4548,7 +4581,7 @@
      * However we need child windows of the applications to be above the IME (Text drag handles).
      * This is a non-strictly hierarcical layering and we need to break out of the Z ordering
      * somehow. We do this by relatively ordering children of the target to the IME in cooperation
-     * with {@link #WindowState#assignLayer}
+     * with {@link WindowState#assignLayer}
      */
     void assignRelativeLayerForImeTargetChild(SurfaceControl.Transaction t, WindowContainer child) {
         child.assignRelativeLayer(t, mImeWindowsContainers.getSurfaceControl(), 1);
diff --git a/services/core/java/com/android/server/wm/DisplayPolicy.java b/services/core/java/com/android/server/wm/DisplayPolicy.java
index 9151ddf..c16f95e 100644
--- a/services/core/java/com/android/server/wm/DisplayPolicy.java
+++ b/services/core/java/com/android/server/wm/DisplayPolicy.java
@@ -16,20 +16,143 @@
 
 package com.android.server.wm;
 
+import static android.app.WindowConfiguration.ACTIVITY_TYPE_HOME;
+import static android.app.WindowConfiguration.ACTIVITY_TYPE_STANDARD;
+import static android.app.WindowConfiguration.WINDOWING_MODE_FREEFORM;
+import static android.app.WindowConfiguration.WINDOWING_MODE_FULLSCREEN;
+import static android.app.WindowConfiguration.WINDOWING_MODE_SPLIT_SCREEN_PRIMARY;
+import static android.app.WindowConfiguration.WINDOWING_MODE_SPLIT_SCREEN_SECONDARY;
+import static android.app.WindowConfiguration.WINDOWING_MODE_UNDEFINED;
+import static android.content.res.Configuration.UI_MODE_TYPE_CAR;
+import static android.content.res.Configuration.UI_MODE_TYPE_MASK;
+import static android.view.ViewGroup.LayoutParams.MATCH_PARENT;
+import static android.view.WindowManager.INPUT_CONSUMER_NAVIGATION;
+import static android.view.WindowManager.LayoutParams.FIRST_APPLICATION_WINDOW;
+import static android.view.WindowManager.LayoutParams.FIRST_SYSTEM_WINDOW;
+import static android.view.WindowManager.LayoutParams.FLAG_ALLOW_LOCK_WHILE_SCREEN_ON;
+import static android.view.WindowManager.LayoutParams.FLAG_DRAWS_SYSTEM_BAR_BACKGROUNDS;
+import static android.view.WindowManager.LayoutParams.FLAG_FORCE_NOT_FULLSCREEN;
+import static android.view.WindowManager.LayoutParams.FLAG_FULLSCREEN;
+import static android.view.WindowManager.LayoutParams.FLAG_LAYOUT_ATTACHED_IN_DECOR;
+import static android.view.WindowManager.LayoutParams.FLAG_LAYOUT_INSET_DECOR;
+import static android.view.WindowManager.LayoutParams.FLAG_LAYOUT_IN_OVERSCAN;
+import static android.view.WindowManager.LayoutParams.FLAG_LAYOUT_IN_SCREEN;
+import static android.view.WindowManager.LayoutParams.FLAG_LAYOUT_NO_LIMITS;
+import static android.view.WindowManager.LayoutParams.FLAG_TRANSLUCENT_NAVIGATION;
+import static android.view.WindowManager.LayoutParams.FLAG_TRANSLUCENT_STATUS;
+import static android.view.WindowManager.LayoutParams.LAST_APPLICATION_WINDOW;
+import static android.view.WindowManager.LayoutParams.LAST_SUB_WINDOW;
+import static android.view.WindowManager.LayoutParams.LAYOUT_IN_DISPLAY_CUTOUT_MODE_ALWAYS;
+import static android.view.WindowManager.LayoutParams.LAYOUT_IN_DISPLAY_CUTOUT_MODE_DEFAULT;
+import static android.view.WindowManager.LayoutParams.PRIVATE_FLAG_ACQUIRES_SLEEP_TOKEN;
+import static android.view.WindowManager.LayoutParams.PRIVATE_FLAG_FORCE_DRAW_STATUS_BAR_BACKGROUND;
+import static android.view.WindowManager.LayoutParams.PRIVATE_FLAG_FORCE_STATUS_BAR_VISIBLE_TRANSPARENT;
+import static android.view.WindowManager.LayoutParams.PRIVATE_FLAG_INHERIT_TRANSLUCENT_DECOR;
+import static android.view.WindowManager.LayoutParams.PRIVATE_FLAG_IS_SCREEN_DECOR;
+import static android.view.WindowManager.LayoutParams.PRIVATE_FLAG_KEYGUARD;
+import static android.view.WindowManager.LayoutParams.PRIVATE_FLAG_STATUS_FORCE_SHOW_NAVIGATION;
+import static android.view.WindowManager.LayoutParams.ROTATION_ANIMATION_CROSSFADE;
+import static android.view.WindowManager.LayoutParams.ROTATION_ANIMATION_JUMPCUT;
+import static android.view.WindowManager.LayoutParams.ROTATION_ANIMATION_ROTATE;
+import static android.view.WindowManager.LayoutParams.ROTATION_ANIMATION_SEAMLESS;
+import static android.view.WindowManager.LayoutParams.SOFT_INPUT_ADJUST_NOTHING;
+import static android.view.WindowManager.LayoutParams.SOFT_INPUT_ADJUST_RESIZE;
+import static android.view.WindowManager.LayoutParams.SOFT_INPUT_MASK_ADJUST;
+import static android.view.WindowManager.LayoutParams.TYPE_BASE_APPLICATION;
+import static android.view.WindowManager.LayoutParams.TYPE_BOOT_PROGRESS;
+import static android.view.WindowManager.LayoutParams.TYPE_DOCK_DIVIDER;
+import static android.view.WindowManager.LayoutParams.TYPE_DREAM;
+import static android.view.WindowManager.LayoutParams.TYPE_INPUT_CONSUMER;
+import static android.view.WindowManager.LayoutParams.TYPE_INPUT_METHOD;
+import static android.view.WindowManager.LayoutParams.TYPE_NAVIGATION_BAR;
+import static android.view.WindowManager.LayoutParams.TYPE_NAVIGATION_BAR_PANEL;
+import static android.view.WindowManager.LayoutParams.TYPE_SCREENSHOT;
+import static android.view.WindowManager.LayoutParams.TYPE_SECURE_SYSTEM_OVERLAY;
+import static android.view.WindowManager.LayoutParams.TYPE_STATUS_BAR;
+import static android.view.WindowManager.LayoutParams.TYPE_STATUS_BAR_PANEL;
+import static android.view.WindowManager.LayoutParams.TYPE_STATUS_BAR_SUB_PANEL;
+import static android.view.WindowManager.LayoutParams.TYPE_SYSTEM_ALERT;
+import static android.view.WindowManager.LayoutParams.TYPE_SYSTEM_ERROR;
+import static android.view.WindowManager.LayoutParams.TYPE_SYSTEM_OVERLAY;
+import static android.view.WindowManager.LayoutParams.TYPE_TOAST;
+import static android.view.WindowManager.LayoutParams.TYPE_VOICE_INTERACTION;
+import static android.view.WindowManager.LayoutParams.TYPE_VOICE_INTERACTION_STARTING;
+import static android.view.WindowManager.LayoutParams.TYPE_VOLUME_OVERLAY;
+import static android.view.WindowManager.LayoutParams.TYPE_WALLPAPER;
+import static android.view.WindowManagerGlobal.ADD_OKAY;
 import static android.view.WindowManagerPolicyConstants.ACTION_HDMI_PLUGGED;
 import static android.view.WindowManagerPolicyConstants.EXTRA_HDMI_PLUGGED_STATE;
+import static android.view.WindowManagerPolicyConstants.NAV_BAR_BOTTOM;
+import static android.view.WindowManagerPolicyConstants.NAV_BAR_LEFT;
+import static android.view.WindowManagerPolicyConstants.NAV_BAR_RIGHT;
+
+import static com.android.server.policy.PhoneWindowManager.TOAST_WINDOW_TIMEOUT;
+import static com.android.server.policy.WindowManagerPolicy.FINISH_LAYOUT_REDO_LAYOUT;
+import static com.android.server.policy.WindowManagerPolicy.TRANSIT_ENTER;
+import static com.android.server.policy.WindowManagerPolicy.TRANSIT_EXIT;
+import static com.android.server.policy.WindowManagerPolicy.TRANSIT_HIDE;
+import static com.android.server.policy.WindowManagerPolicy.TRANSIT_PREVIEW_DONE;
+import static com.android.server.policy.WindowManagerPolicy.TRANSIT_SHOW;
 import static com.android.server.policy.WindowManagerPolicy.WindowManagerFuncs.LID_ABSENT;
+import static com.android.server.wm.ActivityTaskManagerInternal.SleepToken;
+import static com.android.server.wm.WindowManagerDebugConfig.DEBUG_ANIM;
+import static com.android.server.wm.WindowManagerDebugConfig.DEBUG_LAYOUT;
 import static com.android.server.wm.WindowManagerDebugConfig.DEBUG_SCREEN_ON;
 import static com.android.server.wm.WindowManagerDebugConfig.TAG_WITH_CLASS_NAME;
 import static com.android.server.wm.WindowManagerDebugConfig.TAG_WM;
+import static com.android.server.wm.WindowManagerService.localLOGV;
 
+import android.annotation.Nullable;
+import android.app.ActivityManager;
+import android.app.ActivityThread;
+import android.app.StatusBarManager;
+import android.content.Context;
 import android.content.Intent;
+import android.content.res.Resources;
+import android.graphics.Rect;
+import android.hardware.input.InputManager;
+import android.hardware.power.V1_0.PowerHint;
+import android.os.Handler;
+import android.os.Looper;
+import android.os.Message;
+import android.os.SystemClock;
 import android.os.SystemProperties;
 import android.os.UserHandle;
+import android.util.ArraySet;
+import android.util.PrintWriterPrinter;
 import android.util.Slog;
+import android.view.DisplayCutout;
+import android.view.Gravity;
+import android.view.IApplicationToken;
+import android.view.InputChannel;
+import android.view.InputDevice;
+import android.view.InputEvent;
+import android.view.InputEventReceiver;
+import android.view.MotionEvent;
+import android.view.PointerIcon;
+import android.view.Surface;
+import android.view.View;
+import android.view.WindowManager;
+import android.view.WindowManager.LayoutParams;
+import android.view.WindowManagerGlobal;
+import android.view.WindowManagerPolicyConstants;
+import android.view.accessibility.AccessibilityManager;
 
+import com.android.internal.R;
+import com.android.internal.annotations.GuardedBy;
+import com.android.internal.annotations.VisibleForTesting;
+import com.android.internal.util.ScreenShapeHelper;
+import com.android.internal.util.ScreenshotHelper;
+import com.android.server.LocalServices;
+import com.android.server.UiThread;
+import com.android.server.policy.WindowManagerPolicy;
+import com.android.server.policy.WindowManagerPolicy.InputConsumer;
+import com.android.server.policy.WindowManagerPolicy.NavigationBarPosition;
 import com.android.server.policy.WindowManagerPolicy.ScreenOnListener;
 import com.android.server.policy.WindowManagerPolicy.WindowManagerFuncs;
+import com.android.server.policy.WindowOrientationListener;
+import com.android.server.statusbar.StatusBarManagerInternal;
+import com.android.server.wm.utils.InsetUtils;
 
 import java.io.PrintWriter;
 
@@ -38,12 +161,61 @@
  */
 public class DisplayPolicy {
     private static final String TAG = TAG_WITH_CLASS_NAME ? "DisplayPolicy" : TAG_WM;
+    private static final boolean DEBUG = false;
+
+    private static final boolean ALTERNATE_CAR_MODE_NAV_SIZE = false;
+
+    // The panic gesture may become active only after the keyguard is dismissed and the immersive
+    // app shows again. If that doesn't happen for 30s we drop the gesture.
+    private static final long PANIC_GESTURE_EXPIRATION = 30000;
+
+    // Controls navigation bar opacity depending on which workspace stacks are currently
+    // visible.
+    // Nav bar is always opaque when either the freeform stack or docked stack is visible.
+    private static final int NAV_BAR_OPAQUE_WHEN_FREEFORM_OR_DOCKED = 0;
+    // Nav bar is always translucent when the freeform stack is visible, otherwise always opaque.
+    private static final int NAV_BAR_TRANSLUCENT_WHEN_FREEFORM_OPAQUE_OTHERWISE = 1;
+
+    /**
+     * These are the system UI flags that, when changing, can cause the layout
+     * of the screen to change.
+     */
+    private static final int SYSTEM_UI_CHANGING_LAYOUT =
+            View.SYSTEM_UI_FLAG_HIDE_NAVIGATION
+                    | View.SYSTEM_UI_FLAG_FULLSCREEN
+                    | View.STATUS_BAR_TRANSLUCENT
+                    | View.NAVIGATION_BAR_TRANSLUCENT
+                    | View.STATUS_BAR_TRANSPARENT
+                    | View.NAVIGATION_BAR_TRANSPARENT;
 
     private final WindowManagerService mService;
+    private final Context mContext;
+    private final DisplayContent mDisplayContent;
     private final Object mLock;
+    private final Handler mHandler;
 
     private final boolean mCarDockEnablesAccelerometer;
     private final boolean mDeskDockEnablesAccelerometer;
+    private final boolean mTranslucentDecorEnabled;
+    private final AccessibilityManager mAccessibilityManager;
+    private final ImmersiveModeConfirmation mImmersiveModeConfirmation;
+    private final ScreenshotHelper mScreenshotHelper;
+
+    private final Object mServiceAcquireLock = new Object();
+    private StatusBarManagerInternal mStatusBarManagerInternal;
+
+    private StatusBarManagerInternal getStatusBarManagerInternal() {
+        synchronized (mServiceAcquireLock) {
+            if (mStatusBarManagerInternal == null) {
+                mStatusBarManagerInternal =
+                        LocalServices.getService(StatusBarManagerInternal.class);
+            }
+            return mStatusBarManagerInternal;
+        }
+    }
+
+    @VisibleForTesting
+    private final SystemGesturesPointerEventListener mSystemGestures;
 
     private volatile int mLidState = LID_ABSENT;
     private volatile int mDockMode = Intent.EXTRA_DOCK_STATE_UNDOCKED;
@@ -64,32 +236,311 @@
     private volatile boolean mKeyguardDrawComplete;
     private volatile boolean mWindowManagerDrawComplete;
 
-    DisplayPolicy(WindowManagerService service) {
+    private final ArraySet<WindowState> mScreenDecorWindows = new ArraySet<>();
+    private WindowState mStatusBar = null;
+    private final int[] mStatusBarHeightForRotation = new int[4];
+    private WindowState mNavigationBar = null;
+    @NavigationBarPosition
+    private int mNavigationBarPosition = NAV_BAR_BOTTOM;
+    private int[] mNavigationBarHeightForRotationDefault = new int[4];
+    private int[] mNavigationBarWidthForRotationDefault = new int[4];
+    private int[] mNavigationBarHeightForRotationInCarMode = new int[4];
+    private int[] mNavigationBarWidthForRotationInCarMode = new int[4];
+
+    private final StatusBarController mStatusBarController = new StatusBarController();
+
+    private final BarController mNavigationBarController = new BarController("NavigationBar",
+            View.NAVIGATION_BAR_TRANSIENT,
+            View.NAVIGATION_BAR_UNHIDE,
+            View.NAVIGATION_BAR_TRANSLUCENT,
+            StatusBarManager.WINDOW_NAVIGATION_BAR,
+            FLAG_TRANSLUCENT_NAVIGATION,
+            View.NAVIGATION_BAR_TRANSPARENT);
+
+    private final BarController.OnBarVisibilityChangedListener mNavBarVisibilityListener =
+            new BarController.OnBarVisibilityChangedListener() {
+                @Override
+                public void onBarVisibilityChanged(boolean visible) {
+                    if (mAccessibilityManager == null) {
+                        return;
+                    }
+                    mAccessibilityManager.notifyAccessibilityButtonVisibilityChanged(visible);
+                }
+            };
+
+    // EXPERIMENT TODO(b/113952590): Remove once experiment in bug is completed
+    private NavigationBarExperiments mExperiments = new NavigationBarExperiments();
+    // EXPERIMENT END
+
+    @GuardedBy("mHandler")
+    private SleepToken mDreamingSleepToken;
+
+    @GuardedBy("mHandler")
+    private SleepToken mWindowSleepToken;
+
+    private final Runnable mAcquireSleepTokenRunnable;
+    private final Runnable mReleaseSleepTokenRunnable;
+
+    // The windows we were told about in focusChanged.
+    private WindowState mFocusedWindow;
+    private WindowState mLastFocusedWindow;
+
+    IApplicationToken mFocusedApp;
+
+    int mLastSystemUiFlags;
+    // Bits that we are in the process of clearing, so we want to prevent
+    // them from being set by applications until everything has been updated
+    // to have them clear.
+    private int mResettingSystemUiFlags = 0;
+    // Bits that we are currently always keeping cleared.
+    private int mForceClearedSystemUiFlags = 0;
+    private int mLastFullscreenStackSysUiFlags;
+    private int mLastDockedStackSysUiFlags;
+    private final Rect mNonDockedStackBounds = new Rect();
+    private final Rect mDockedStackBounds = new Rect();
+    private final Rect mLastNonDockedStackBounds = new Rect();
+    private final Rect mLastDockedStackBounds = new Rect();
+
+    // What we last reported to system UI about whether the compatibility
+    // menu needs to be displayed.
+    private boolean mLastFocusNeedsMenu = false;
+    // If nonzero, a panic gesture was performed at that time in uptime millis and is still pending.
+    private long mPendingPanicGestureUptime;
+
+    private static final Rect sTmpDisplayCutoutSafeExceptMaybeBarsRect = new Rect();
+    private static final Rect sTmpRect = new Rect();
+    private static final Rect sTmpDockedFrame = new Rect();
+    private static final Rect sTmpNavFrame = new Rect();
+    private static final Rect sTmpLastParentFrame = new Rect();
+
+    private WindowState mTopFullscreenOpaqueWindowState;
+    private WindowState mTopFullscreenOpaqueOrDimmingWindowState;
+    private WindowState mTopDockedOpaqueWindowState;
+    private WindowState mTopDockedOpaqueOrDimmingWindowState;
+    private boolean mTopIsFullscreen;
+    private boolean mForceStatusBar;
+    private boolean mForceStatusBarFromKeyguard;
+    private boolean mForceStatusBarTransparent;
+    private int mNavBarOpacityMode = NAV_BAR_OPAQUE_WHEN_FREEFORM_OR_DOCKED;
+    private boolean mForcingShowNavBar;
+    private int mForcingShowNavBarLayer;
+    private boolean mForceShowSystemBars;
+
+    private boolean mShowingDream;
+    private boolean mLastShowingDream;
+    private boolean mDreamingLockscreen;
+    private boolean mDreamingSleepTokenNeeded;
+    private boolean mWindowSleepTokenNeeded;
+    private boolean mLastWindowSleepTokenNeeded;
+    private boolean mAllowLockscreenWhenOn;
+
+    private InputConsumer mInputConsumer = null;
+
+    // -------- PolicyHandler --------
+    private static final int MSG_UPDATE_DREAMING_SLEEP_TOKEN = 1;
+    private static final int MSG_REQUEST_TRANSIENT_BARS = 2;
+    private static final int MSG_DISPOSE_INPUT_CONSUMER = 3;
+
+    private static final int MSG_REQUEST_TRANSIENT_BARS_ARG_STATUS = 0;
+    private static final int MSG_REQUEST_TRANSIENT_BARS_ARG_NAVIGATION = 1;
+
+    private class PolicyHandler extends Handler {
+
+        PolicyHandler(Looper looper) {
+            super(looper);
+        }
+
+        @Override
+        public void handleMessage(Message msg) {
+            switch (msg.what) {
+                case MSG_UPDATE_DREAMING_SLEEP_TOKEN:
+                    updateDreamingSleepToken(msg.arg1 != 0);
+                    break;
+                case MSG_REQUEST_TRANSIENT_BARS:
+                    WindowState targetBar = (msg.arg1 == MSG_REQUEST_TRANSIENT_BARS_ARG_STATUS)
+                            ? mStatusBar : mNavigationBar;
+                    if (targetBar != null) {
+                        requestTransientBars(targetBar);
+                    }
+                    break;
+                case MSG_DISPOSE_INPUT_CONSUMER:
+                    disposeInputConsumer((InputConsumer) msg.obj);
+                    break;
+            }
+        }
+    }
+
+    DisplayPolicy(WindowManagerService service, DisplayContent displayContent) {
         mService = service;
+        mContext = displayContent.isDefaultDisplay ? service.mContext
+                : service.mContext.createDisplayContext(displayContent.getDisplay());
+        mDisplayContent = displayContent;
         mLock = service.getWindowManagerLock();
-        mCarDockEnablesAccelerometer = service.mContext.getResources().getBoolean(
-                com.android.internal.R.bool.config_carDockEnablesAccelerometer);
-        mDeskDockEnablesAccelerometer = service.mContext.getResources().getBoolean(
-                com.android.internal.R.bool.config_deskDockEnablesAccelerometer);
+
+        final Resources r = mContext.getResources();
+        mCarDockEnablesAccelerometer = r.getBoolean(R.bool.config_carDockEnablesAccelerometer);
+        mDeskDockEnablesAccelerometer = r.getBoolean(R.bool.config_deskDockEnablesAccelerometer);
+        mTranslucentDecorEnabled = r.getBoolean(R.bool.config_enableTranslucentDecor);
+        updateConfigurationDependentBehaviors();
+
+        mAccessibilityManager = (AccessibilityManager) mContext.getSystemService(
+                Context.ACCESSIBILITY_SERVICE);
+        if (!displayContent.isDefaultDisplay) {
+            mAwake = true;
+            mScreenOnEarly = true;
+            mScreenOnFully = true;
+        }
+
+        final Looper looper = UiThread.getHandler().getLooper();
+        mHandler = new PolicyHandler(looper);
+        mSystemGestures = new SystemGesturesPointerEventListener(mContext, mHandler,
+                new SystemGesturesPointerEventListener.Callbacks() {
+                    @Override
+                    public void onSwipeFromTop() {
+                        if (mStatusBar != null) {
+                            requestTransientBars(mStatusBar);
+                        }
+                    }
+
+                    @Override
+                    public void onSwipeFromBottom() {
+                        if (mNavigationBar != null
+                                && mNavigationBarPosition == NAV_BAR_BOTTOM) {
+                            requestTransientBars(mNavigationBar);
+                        }
+                    }
+
+                    @Override
+                    public void onSwipeFromRight() {
+                        if (mNavigationBar != null && mNavigationBarPosition == NAV_BAR_RIGHT) {
+                            requestTransientBars(mNavigationBar);
+                        }
+                    }
+
+                    @Override
+                    public void onSwipeFromLeft() {
+                        if (mNavigationBar != null && mNavigationBarPosition == NAV_BAR_LEFT) {
+                            requestTransientBars(mNavigationBar);
+                        }
+                    }
+
+                    @Override
+                    public void onFling(int duration) {
+                        if (mService.mPowerManagerInternal != null) {
+                            mService.mPowerManagerInternal.powerHint(
+                                    PowerHint.INTERACTION, duration);
+                        }
+                    }
+
+                    @Override
+                    public void onDebug() {
+                        // no-op
+                    }
+
+                    private WindowOrientationListener getOrientationListener() {
+                        final DisplayRotation rotation = mDisplayContent.getDisplayRotation();
+                        return rotation != null ? rotation.getOrientationListener() : null;
+                    }
+
+                    @Override
+                    public void onDown() {
+                        final WindowOrientationListener listener = getOrientationListener();
+                        if (listener != null) {
+                            listener.onTouchStart();
+                        }
+                    }
+
+                    @Override
+                    public void onUpOrCancel() {
+                        final WindowOrientationListener listener = getOrientationListener();
+                        if (listener != null) {
+                            listener.onTouchEnd();
+                        }
+                    }
+
+                    @Override
+                    public void onMouseHoverAtTop() {
+                        mHandler.removeMessages(MSG_REQUEST_TRANSIENT_BARS);
+                        Message msg = mHandler.obtainMessage(MSG_REQUEST_TRANSIENT_BARS);
+                        msg.arg1 = MSG_REQUEST_TRANSIENT_BARS_ARG_STATUS;
+                        mHandler.sendMessageDelayed(msg, 500 /* delayMillis */);
+                    }
+
+                    @Override
+                    public void onMouseHoverAtBottom() {
+                        mHandler.removeMessages(MSG_REQUEST_TRANSIENT_BARS);
+                        Message msg = mHandler.obtainMessage(MSG_REQUEST_TRANSIENT_BARS);
+                        msg.arg1 = MSG_REQUEST_TRANSIENT_BARS_ARG_NAVIGATION;
+                        mHandler.sendMessageDelayed(msg, 500 /* delayMillis */);
+                    }
+
+                    @Override
+                    public void onMouseLeaveFromEdge() {
+                        mHandler.removeMessages(MSG_REQUEST_TRANSIENT_BARS);
+                    }
+                });
+        displayContent.registerPointerEventListener(mSystemGestures);
+        displayContent.mAppTransition.registerListenerLocked(
+                mStatusBarController.getAppTransitionListener());
+        mImmersiveModeConfirmation = new ImmersiveModeConfirmation(mContext, looper,
+                mService.mVrModeEnabled);
+        mAcquireSleepTokenRunnable = () -> {
+            if (mWindowSleepToken != null) {
+                return;
+            }
+            final int displayId = displayContent.getDisplayId();
+            mWindowSleepToken = service.mAtmInternal.acquireSleepToken(
+                    "WindowSleepTokenOnDisplay" + displayId, displayId);
+        };
+        mReleaseSleepTokenRunnable = () -> {
+            if (mWindowSleepToken == null) {
+                return;
+            }
+            mWindowSleepToken.release();
+            mWindowSleepToken = null;
+        };
+
+        // TODO: Make it can take screenshot on external display
+        mScreenshotHelper = displayContent.isDefaultDisplay
+                ? new ScreenshotHelper(mContext) : null;
+    }
+
+    void systemReady() {
+        mSystemGestures.systemReady();
+    }
+
+    private int getDisplayId() {
+        return mDisplayContent.getDisplayId();
+    }
+
+    void onDisplayRemoved() {
+        mDisplayContent.unregisterPointerEventListener(mSystemGestures);
     }
 
     void configure(int width, int height, int shortSizeDp) {
         // Allow the navigation bar to move on non-square small devices (phones).
         mNavigationBarCanMove = width != height && shortSizeDp < 600;
 
-        mHasNavigationBar = mService.mContext.getResources().getBoolean(
-                com.android.internal.R.bool.config_showNavigationBar);
+        if (mDisplayContent.isDefaultDisplay) {
+            mHasNavigationBar = mContext.getResources().getBoolean(R.bool.config_showNavigationBar);
 
-        // Allow a system property to override this. Used by the emulator.
-        // See also hasNavigationBar().
-        String navBarOverride = SystemProperties.get("qemu.hw.mainkeys");
-        if ("1".equals(navBarOverride)) {
-            mHasNavigationBar = false;
-        } else if ("0".equals(navBarOverride)) {
-            mHasNavigationBar = true;
+            // Allow a system property to override this. Used by the emulator.
+            // See also hasNavigationBar().
+            String navBarOverride = SystemProperties.get("qemu.hw.mainkeys");
+            if ("1".equals(navBarOverride)) {
+                mHasNavigationBar = false;
+            } else if ("0".equals(navBarOverride)) {
+                mHasNavigationBar = true;
+            }
+        } else {
+            mHasNavigationBar = mDisplayContent.getDisplay().supportsSystemDecorations();
         }
     }
 
+    void updateConfigurationDependentBehaviors() {
+        mNavBarOpacityMode = mContext.getResources().getInteger(R.integer.config_navBarOpacityMode);
+    }
+
     public void setHdmiPlugged(boolean plugged) {
         setHdmiPlugged(plugged, false /* force */);
     }
@@ -101,7 +552,7 @@
             final Intent intent = new Intent(ACTION_HDMI_PLUGGED);
             intent.addFlags(Intent.FLAG_RECEIVER_REGISTERED_ONLY_BEFORE_BOOT);
             intent.putExtra(EXTRA_HDMI_PLUGGED_STATE, plugged);
-            mService.mContext.sendStickyBroadcastAsUser(intent, UserHandle.ALL);
+            mContext.sendStickyBroadcastAsUser(intent, UserHandle.ALL);
         }
     }
 
@@ -244,17 +695,2642 @@
         return true;
     }
 
+    /**
+     * 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.
+     *
+     * @param attrs The window layout parameters to be modified.  These values
+     * are modified in-place.
+     */
+    public void adjustWindowParamsLw(WindowState win, WindowManager.LayoutParams attrs,
+            boolean hasStatusBarServicePermission) {
+
+        final boolean isScreenDecor = (attrs.privateFlags & PRIVATE_FLAG_IS_SCREEN_DECOR) != 0;
+        if (mScreenDecorWindows.contains(win)) {
+            if (!isScreenDecor) {
+                // No longer has the flag set, so remove from the set.
+                mScreenDecorWindows.remove(win);
+            }
+        } else if (isScreenDecor && hasStatusBarServicePermission) {
+            mScreenDecorWindows.add(win);
+        }
+
+        switch (attrs.type) {
+            case TYPE_SYSTEM_OVERLAY:
+            case TYPE_SECURE_SYSTEM_OVERLAY:
+                // These types of windows can't receive input events.
+                attrs.flags |= WindowManager.LayoutParams.FLAG_NOT_FOCUSABLE
+                        | WindowManager.LayoutParams.FLAG_NOT_TOUCHABLE;
+                attrs.flags &= ~WindowManager.LayoutParams.FLAG_WATCH_OUTSIDE_TOUCH;
+                break;
+            case TYPE_DREAM:
+            case TYPE_WALLPAPER:
+                // Dreams and wallpapers don't have an app window token and can thus not be
+                // letterboxed. Hence always let them extend under the cutout.
+                attrs.layoutInDisplayCutoutMode = LAYOUT_IN_DISPLAY_CUTOUT_MODE_ALWAYS;
+                break;
+            case TYPE_STATUS_BAR:
+
+                // If the Keyguard is in a hidden state (occluded by another window), we force to
+                // remove the wallpaper and keyguard flag so that any change in-flight after setting
+                // the keyguard as occluded wouldn't set these flags again.
+                // See {@link #processKeyguardSetHiddenResultLw}.
+                if (mService.mPolicy.isKeyguardOccluded()) {
+                    attrs.flags &= ~WindowManager.LayoutParams.FLAG_SHOW_WALLPAPER;
+                    attrs.privateFlags &= ~WindowManager.LayoutParams.PRIVATE_FLAG_KEYGUARD;
+                }
+                break;
+
+            case TYPE_SCREENSHOT:
+                attrs.flags |= WindowManager.LayoutParams.FLAG_NOT_FOCUSABLE;
+                break;
+
+            case TYPE_TOAST:
+                // While apps should use the dedicated toast APIs to add such windows
+                // it possible legacy apps to add the window directly. Therefore, we
+                // make windows added directly by the app behave as a toast as much
+                // as possible in terms of timeout and animation.
+                if (attrs.hideTimeoutMilliseconds < 0
+                        || attrs.hideTimeoutMilliseconds > TOAST_WINDOW_TIMEOUT) {
+                    attrs.hideTimeoutMilliseconds = TOAST_WINDOW_TIMEOUT;
+                }
+                attrs.windowAnimations = com.android.internal.R.style.Animation_Toast;
+                break;
+        }
+
+        if (attrs.type != TYPE_STATUS_BAR) {
+            // The status bar is the only window allowed to exhibit keyguard behavior.
+            attrs.privateFlags &= ~WindowManager.LayoutParams.PRIVATE_FLAG_KEYGUARD;
+        }
+    }
+
+    /**
+     * Preflight adding a window to the system.
+     *
+     * Currently enforces that three window types are singletons per display:
+     * <ul>
+     * <li>{@link WindowManager.LayoutParams#TYPE_STATUS_BAR}</li>
+     * <li>{@link WindowManager.LayoutParams#TYPE_NAVIGATION_BAR}</li>
+     * </ul>
+     *
+     * @param win The window to be added
+     * @param attrs Information about the window to be added
+     *
+     * @return If ok, WindowManagerImpl.ADD_OKAY.  If too many singletons,
+     * WindowManagerImpl.ADD_MULTIPLE_SINGLETON
+     */
+    public int prepareAddWindowLw(WindowState win, WindowManager.LayoutParams attrs) {
+
+        if ((attrs.privateFlags & PRIVATE_FLAG_IS_SCREEN_DECOR) != 0) {
+            mContext.enforceCallingOrSelfPermission(
+                    android.Manifest.permission.STATUS_BAR_SERVICE,
+                    "DisplayPolicy");
+            mScreenDecorWindows.add(win);
+        }
+
+        switch (attrs.type) {
+            case TYPE_STATUS_BAR:
+                mContext.enforceCallingOrSelfPermission(
+                        android.Manifest.permission.STATUS_BAR_SERVICE,
+                        "DisplayPolicy");
+                if (mStatusBar != null) {
+                    if (mStatusBar.isAlive()) {
+                        return WindowManagerGlobal.ADD_MULTIPLE_SINGLETON;
+                    }
+                }
+                mStatusBar = win;
+                mStatusBarController.setWindow(win);
+                if (mDisplayContent.isDefaultDisplay) {
+                    mService.mPolicy.setKeyguardCandidateLw(win);
+                }
+                break;
+            case TYPE_NAVIGATION_BAR:
+                mContext.enforceCallingOrSelfPermission(
+                        android.Manifest.permission.STATUS_BAR_SERVICE,
+                        "DisplayPolicy");
+                if (mNavigationBar != null) {
+                    if (mNavigationBar.isAlive()) {
+                        return WindowManagerGlobal.ADD_MULTIPLE_SINGLETON;
+                    }
+                }
+                mNavigationBar = win;
+                mNavigationBarController.setWindow(win);
+                mNavigationBarController.setOnBarVisibilityChangedListener(
+                        mNavBarVisibilityListener, true);
+                if (DEBUG_LAYOUT) Slog.i(TAG, "NAVIGATION BAR: " + mNavigationBar);
+                break;
+            case TYPE_NAVIGATION_BAR_PANEL:
+            case TYPE_STATUS_BAR_PANEL:
+            case TYPE_STATUS_BAR_SUB_PANEL:
+            case TYPE_VOICE_INTERACTION_STARTING:
+                mContext.enforceCallingOrSelfPermission(
+                        android.Manifest.permission.STATUS_BAR_SERVICE,
+                        "DisplayPolicy");
+                break;
+        }
+        return ADD_OKAY;
+    }
+
+    /**
+     * Called when a window is being removed from a window manager.  Must not
+     * throw an exception -- clean up as much as possible.
+     *
+     * @param win The window being removed.
+     */
+    public void removeWindowLw(WindowState win) {
+        if (mStatusBar == win) {
+            mStatusBar = null;
+            mStatusBarController.setWindow(null);
+            if (mDisplayContent.isDefaultDisplay) {
+                mService.mPolicy.setKeyguardCandidateLw(null);
+            }
+        } else if (mNavigationBar == win) {
+            mNavigationBar = null;
+            mNavigationBarController.setWindow(null);
+        }
+        if (mLastFocusedWindow == win) {
+            mLastFocusedWindow = null;
+        }
+        mScreenDecorWindows.remove(win);
+    }
+
+    /**
+     * Control the animation to run when a window's state changes.  Return a
+     * non-0 number to force the animation to a specific resource ID, or 0
+     * to use the default animation.
+     *
+     * @param win The window that is changing.
+     * @param transit What is happening to the window:
+     *                {@link com.android.server.policy.WindowManagerPolicy#TRANSIT_ENTER},
+     *                {@link com.android.server.policy.WindowManagerPolicy#TRANSIT_EXIT},
+     *                {@link com.android.server.policy.WindowManagerPolicy#TRANSIT_SHOW}, or
+     *                {@link com.android.server.policy.WindowManagerPolicy#TRANSIT_HIDE}.
+     *
+     * @return Resource ID of the actual animation to use, or 0 for none.
+     */
+    public int selectAnimationLw(WindowState win, int transit) {
+        if (DEBUG_ANIM) Slog.i(TAG, "selectAnimation in " + win
+                + ": transit=" + transit);
+        if (win == mStatusBar) {
+            final boolean isKeyguard = (win.getAttrs().privateFlags & PRIVATE_FLAG_KEYGUARD) != 0;
+            final boolean expanded = win.getAttrs().height == MATCH_PARENT
+                    && win.getAttrs().width == MATCH_PARENT;
+            if (isKeyguard || expanded) {
+                return -1;
+            }
+            if (transit == TRANSIT_EXIT
+                    || transit == TRANSIT_HIDE) {
+                return R.anim.dock_top_exit;
+            } else if (transit == TRANSIT_ENTER
+                    || transit == TRANSIT_SHOW) {
+                return R.anim.dock_top_enter;
+            }
+        } else if (win == mNavigationBar) {
+            if (win.getAttrs().windowAnimations != 0) {
+                return 0;
+            }
+            // This can be on either the bottom or the right or the left.
+            if (mNavigationBarPosition == NAV_BAR_BOTTOM) {
+                if (transit == TRANSIT_EXIT
+                        || transit == TRANSIT_HIDE) {
+                    if (mService.mPolicy.isKeyguardShowingAndNotOccluded()) {
+                        return R.anim.dock_bottom_exit_keyguard;
+                    } else {
+                        return R.anim.dock_bottom_exit;
+                    }
+                } else if (transit == TRANSIT_ENTER
+                        || transit == TRANSIT_SHOW) {
+                    return R.anim.dock_bottom_enter;
+                }
+            } else if (mNavigationBarPosition == NAV_BAR_RIGHT) {
+                if (transit == TRANSIT_EXIT
+                        || transit == TRANSIT_HIDE) {
+                    return R.anim.dock_right_exit;
+                } else if (transit == TRANSIT_ENTER
+                        || transit == TRANSIT_SHOW) {
+                    return R.anim.dock_right_enter;
+                }
+            } else if (mNavigationBarPosition == NAV_BAR_LEFT) {
+                if (transit == TRANSIT_EXIT
+                        || transit == TRANSIT_HIDE) {
+                    return R.anim.dock_left_exit;
+                } else if (transit == TRANSIT_ENTER
+                        || transit == TRANSIT_SHOW) {
+                    return R.anim.dock_left_enter;
+                }
+            }
+        } else if (win.getAttrs().type == TYPE_DOCK_DIVIDER) {
+            return selectDockedDividerAnimationLw(win, transit);
+        }
+
+        if (transit == TRANSIT_PREVIEW_DONE) {
+            if (win.hasAppShownWindows()) {
+                if (DEBUG_ANIM) Slog.i(TAG, "**** STARTING EXIT");
+                return R.anim.app_starting_exit;
+            }
+        } else if (win.getAttrs().type == TYPE_DREAM && mDreamingLockscreen
+                && transit == TRANSIT_ENTER) {
+            // Special case: we are animating in a dream, while the keyguard
+            // is shown.  We don't want an animation on the dream, because
+            // we need it shown immediately with the keyguard animating away
+            // to reveal it.
+            return -1;
+        }
+
+        return 0;
+    }
+
+    private int selectDockedDividerAnimationLw(WindowState win, int transit) {
+        int insets = mDisplayContent.getDockedDividerController().getContentInsets();
+
+        // If the divider is behind the navigation bar, don't animate.
+        final Rect frame = win.getFrameLw();
+        final boolean behindNavBar = mNavigationBar != null
+                && ((mNavigationBarPosition == NAV_BAR_BOTTOM
+                && frame.top + insets >= mNavigationBar.getFrameLw().top)
+                || (mNavigationBarPosition == NAV_BAR_RIGHT
+                && frame.left + insets >= mNavigationBar.getFrameLw().left)
+                || (mNavigationBarPosition == NAV_BAR_LEFT
+                && frame.right - insets <= mNavigationBar.getFrameLw().right));
+        final boolean landscape = frame.height() > frame.width();
+        final boolean offscreenLandscape = landscape && (frame.right - insets <= 0
+                || frame.left + insets >= win.getDisplayFrameLw().right);
+        final boolean offscreenPortrait = !landscape && (frame.top - insets <= 0
+                || frame.bottom + insets >= win.getDisplayFrameLw().bottom);
+        final boolean offscreen = offscreenLandscape || offscreenPortrait;
+        if (behindNavBar || offscreen) {
+            return 0;
+        }
+        if (transit == TRANSIT_ENTER || transit == TRANSIT_SHOW) {
+            return R.anim.fade_in;
+        } else if (transit == TRANSIT_EXIT) {
+            return R.anim.fade_out;
+        } else {
+            return 0;
+        }
+    }
+
+    /**
+     * Determine the animation to run for a rotation transition based on the
+     * top fullscreen windows {@link WindowManager.LayoutParams#rotationAnimation}
+     * and whether it is currently fullscreen and frontmost.
+     *
+     * @param anim The exiting animation resource id is stored in anim[0], the
+     * entering animation resource id is stored in anim[1].
+     */
+    public void selectRotationAnimationLw(int anim[]) {
+        // If the screen is off or non-interactive, force a jumpcut.
+        final boolean forceJumpcut = !mScreenOnFully || !mService.mPolicy.okToAnimate();
+        if (DEBUG_ANIM) Slog.i(TAG, "selectRotationAnimation mTopFullscreen="
+                + mTopFullscreenOpaqueWindowState + " rotationAnimation="
+                + (mTopFullscreenOpaqueWindowState == null
+                ? "0" : mTopFullscreenOpaqueWindowState.getAttrs().rotationAnimation)
+                + " forceJumpcut=" + forceJumpcut);
+        if (forceJumpcut) {
+            anim[0] = R.anim.rotation_animation_jump_exit;
+            anim[1] = R.anim.rotation_animation_enter;
+            return;
+        }
+        if (mTopFullscreenOpaqueWindowState != null) {
+            int animationHint = mTopFullscreenOpaqueWindowState.getRotationAnimationHint();
+            if (animationHint < 0 && mTopIsFullscreen) {
+                animationHint = mTopFullscreenOpaqueWindowState.getAttrs().rotationAnimation;
+            }
+            switch (animationHint) {
+                case ROTATION_ANIMATION_CROSSFADE:
+                case ROTATION_ANIMATION_SEAMLESS: // Crossfade is fallback for seamless.
+                    anim[0] = R.anim.rotation_animation_xfade_exit;
+                    anim[1] = R.anim.rotation_animation_enter;
+                    break;
+                case ROTATION_ANIMATION_JUMPCUT:
+                    anim[0] = R.anim.rotation_animation_jump_exit;
+                    anim[1] = R.anim.rotation_animation_enter;
+                    break;
+                case ROTATION_ANIMATION_ROTATE:
+                default:
+                    anim[0] = anim[1] = 0;
+                    break;
+            }
+        } else {
+            anim[0] = anim[1] = 0;
+        }
+    }
+
+    /**
+     * Validate whether the current top fullscreen has specified the same
+     * {@link WindowManager.LayoutParams#rotationAnimation} value as that
+     * being passed in from the previous top fullscreen window.
+     *
+     * @param exitAnimId exiting resource id from the previous window.
+     * @param enterAnimId entering resource id from the previous window.
+     * @param forceDefault For rotation animations only, if true ignore the
+     * animation values and just return false.
+     * @return true if the previous values are still valid, false if they
+     * should be replaced with the default.
+     */
+    public boolean validateRotationAnimationLw(int exitAnimId, int enterAnimId,
+            boolean forceDefault) {
+        switch (exitAnimId) {
+            case R.anim.rotation_animation_xfade_exit:
+            case R.anim.rotation_animation_jump_exit:
+                // These are the only cases that matter.
+                if (forceDefault) {
+                    return false;
+                }
+                int anim[] = new int[2];
+                selectRotationAnimationLw(anim);
+                return (exitAnimId == anim[0] && enterAnimId == anim[1]);
+            default:
+                return true;
+        }
+    }
+
+    /**
+     * Called when a new system UI visibility is being reported, allowing
+     * the policy to adjust what is actually reported.
+     * @param visibility The raw visibility reported by the status bar.
+     * @return The new desired visibility.
+     */
+    public int adjustSystemUiVisibilityLw(int visibility) {
+        mStatusBarController.adjustSystemUiVisibilityLw(mLastSystemUiFlags, visibility);
+        mNavigationBarController.adjustSystemUiVisibilityLw(mLastSystemUiFlags, visibility);
+
+        // Reset any bits in mForceClearingStatusBarVisibility that
+        // are now clear.
+        mResettingSystemUiFlags &= visibility;
+        // Clear any bits in the new visibility that are currently being
+        // force cleared, before reporting it.
+        return visibility & ~mResettingSystemUiFlags
+                & ~mForceClearedSystemUiFlags;
+    }
+
+    /**
+     * @return true if the navigation bar is forced to stay visible
+     */
+    public boolean isNavBarForcedShownLw(WindowState windowState) {
+        return mForceShowSystemBars;
+    }
+
+    // TODO: Should probably be moved into DisplayFrames.
+    /**
+     * Return the layout hints for a newly added window. These values are computed on the
+     * most recent layout, so they are not guaranteed to be correct.
+     *
+     * @param attrs The LayoutParams of the window.
+     * @param taskBounds The bounds of the task this window is on or {@code null} if no task is
+     *                   associated with the window.
+     * @param displayFrames display frames.
+     * @param floatingStack Whether the window's stack is floating.
+     * @param outFrame The frame of the window.
+     * @param outContentInsets The areas covered by system windows, expressed as positive insets.
+     * @param outStableInsets The areas covered by stable system windows irrespective of their
+     *                        current visibility. Expressed as positive insets.
+     * @param outOutsets The areas that are not real display, but we would like to treat as such.
+     * @param outDisplayCutout The area that has been cut away from the display.
+     * @return Whether to always consume the navigation bar.
+     *         See {@link #isNavBarForcedShownLw(WindowState)}.
+     */
+    public boolean getLayoutHintLw(LayoutParams attrs, Rect taskBounds,
+            DisplayFrames displayFrames, boolean floatingStack, Rect outFrame,
+            Rect outContentInsets, Rect outStableInsets,
+            Rect outOutsets, DisplayCutout.ParcelableWrapper outDisplayCutout) {
+        final int fl = PolicyControl.getWindowFlags(null, attrs);
+        final int pfl = attrs.privateFlags;
+        final int requestedSysUiVis = PolicyControl.getSystemUiVisibility(null, attrs);
+        final int sysUiVis = requestedSysUiVis | getImpliedSysUiFlagsForLayout(attrs);
+        final int displayRotation = displayFrames.mRotation;
+
+        final boolean useOutsets = outOutsets != null && shouldUseOutsets(attrs, fl);
+        if (useOutsets) {
+            int outset = ScreenShapeHelper.getWindowOutsetBottomPx(mContext.getResources());
+            if (outset > 0) {
+                if (displayRotation == Surface.ROTATION_0) {
+                    outOutsets.bottom += outset;
+                } else if (displayRotation == Surface.ROTATION_90) {
+                    outOutsets.right += outset;
+                } else if (displayRotation == Surface.ROTATION_180) {
+                    outOutsets.top += outset;
+                } else if (displayRotation == Surface.ROTATION_270) {
+                    outOutsets.left += outset;
+                }
+            }
+        }
+
+        final boolean layoutInScreen = (fl & FLAG_LAYOUT_IN_SCREEN) != 0;
+        final boolean layoutInScreenAndInsetDecor = layoutInScreen
+                && (fl & FLAG_LAYOUT_INSET_DECOR) != 0;
+        final boolean screenDecor = (pfl & PRIVATE_FLAG_IS_SCREEN_DECOR) != 0;
+
+        if (layoutInScreenAndInsetDecor && !screenDecor) {
+            if ((sysUiVis & View.SYSTEM_UI_FLAG_LAYOUT_HIDE_NAVIGATION) != 0) {
+                outFrame.set(displayFrames.mUnrestricted);
+            } else {
+                outFrame.set(displayFrames.mRestricted);
+            }
+
+            final Rect sf;
+            if (floatingStack) {
+                sf = null;
+            } else {
+                sf = displayFrames.mStable;
+            }
+
+            final Rect cf;
+            if (floatingStack) {
+                cf = null;
+            } else if ((sysUiVis & View.SYSTEM_UI_FLAG_LAYOUT_STABLE) != 0) {
+                if ((fl & FLAG_FULLSCREEN) != 0) {
+                    cf = displayFrames.mStableFullscreen;
+                } else {
+                    cf = displayFrames.mStable;
+                }
+            } else if ((fl & FLAG_FULLSCREEN) != 0 || (fl & FLAG_LAYOUT_IN_OVERSCAN) != 0) {
+                cf = displayFrames.mOverscan;
+            } else {
+                cf = displayFrames.mCurrent;
+            }
+
+            if (taskBounds != null) {
+                outFrame.intersect(taskBounds);
+            }
+            InsetUtils.insetsBetweenFrames(outFrame, cf, outContentInsets);
+            InsetUtils.insetsBetweenFrames(outFrame, sf, outStableInsets);
+            outDisplayCutout.set(displayFrames.mDisplayCutout.calculateRelativeTo(outFrame)
+                    .getDisplayCutout());
+            return mForceShowSystemBars;
+        } else {
+            if (layoutInScreen) {
+                outFrame.set(displayFrames.mUnrestricted);
+            } else {
+                outFrame.set(displayFrames.mStable);
+            }
+            if (taskBounds != null) {
+                outFrame.intersect(taskBounds);
+            }
+
+            outContentInsets.setEmpty();
+            outStableInsets.setEmpty();
+            outDisplayCutout.set(DisplayCutout.NO_CUTOUT);
+            return mForceShowSystemBars;
+        }
+    }
+
+    private static int getImpliedSysUiFlagsForLayout(LayoutParams attrs) {
+        int impliedFlags = 0;
+        if ((attrs.flags & FLAG_DRAWS_SYSTEM_BAR_BACKGROUNDS) != 0) {
+            impliedFlags |= View.SYSTEM_UI_FLAG_LAYOUT_HIDE_NAVIGATION;
+        }
+        final boolean forceWindowDrawsStatusBarBackground =
+                (attrs.privateFlags & PRIVATE_FLAG_FORCE_DRAW_STATUS_BAR_BACKGROUND) != 0;
+        if ((attrs.flags & FLAG_DRAWS_SYSTEM_BAR_BACKGROUNDS) != 0
+                || forceWindowDrawsStatusBarBackground
+                && attrs.height == MATCH_PARENT && attrs.width == MATCH_PARENT) {
+            impliedFlags |= View.SYSTEM_UI_FLAG_LAYOUT_FULLSCREEN;
+        }
+        return impliedFlags;
+    }
+
+    private static boolean shouldUseOutsets(WindowManager.LayoutParams attrs, int fl) {
+        return attrs.type == TYPE_WALLPAPER || (fl & (WindowManager.LayoutParams.FLAG_FULLSCREEN
+                | WindowManager.LayoutParams.FLAG_LAYOUT_IN_OVERSCAN)) != 0;
+    }
+
+    private final Runnable mClearHideNavigationFlag = new Runnable() {
+        @Override
+        public void run() {
+            synchronized (mLock) {
+                mForceClearedSystemUiFlags &= ~View.SYSTEM_UI_FLAG_HIDE_NAVIGATION;
+                mDisplayContent.reevaluateStatusBarVisibility();
+            }
+        }
+    };
+
+    /**
+     * Input handler used while nav bar is hidden.  Captures any touch on the screen,
+     * to determine when the nav bar should be shown and prevent applications from
+     * receiving those touches.
+     */
+    private final class HideNavInputEventReceiver extends InputEventReceiver {
+        HideNavInputEventReceiver(InputChannel inputChannel, Looper looper) {
+            super(inputChannel, looper);
+        }
+
+        @Override
+        public void onInputEvent(InputEvent event) {
+            try {
+                if (event instanceof MotionEvent
+                        && (event.getSource() & InputDevice.SOURCE_CLASS_POINTER) != 0) {
+                    final MotionEvent motionEvent = (MotionEvent) event;
+                    if (motionEvent.getAction() == MotionEvent.ACTION_DOWN) {
+                        // When the user taps down, we re-show the nav bar.
+                        boolean changed = false;
+                        synchronized (mLock) {
+                            if (mInputConsumer == null) {
+                                return;
+                            }
+                            // Any user activity always causes us to show the
+                            // navigation controls, if they had been hidden.
+                            // We also clear the low profile and only content
+                            // flags so that tapping on the screen will atomically
+                            // restore all currently hidden screen decorations.
+                            int newVal = mResettingSystemUiFlags
+                                    | View.SYSTEM_UI_FLAG_HIDE_NAVIGATION
+                                    | View.SYSTEM_UI_FLAG_LOW_PROFILE
+                                    | View.SYSTEM_UI_FLAG_FULLSCREEN;
+                            if (mResettingSystemUiFlags != newVal) {
+                                mResettingSystemUiFlags = newVal;
+                                changed = true;
+                            }
+                            // We don't allow the system's nav bar to be hidden
+                            // again for 1 second, to prevent applications from
+                            // spamming us and keeping it from being shown.
+                            newVal = mForceClearedSystemUiFlags
+                                    | View.SYSTEM_UI_FLAG_HIDE_NAVIGATION;
+                            if (mForceClearedSystemUiFlags != newVal) {
+                                mForceClearedSystemUiFlags = newVal;
+                                changed = true;
+                                mHandler.postDelayed(mClearHideNavigationFlag, 1000);
+                            }
+                            if (changed) {
+                                mDisplayContent.reevaluateStatusBarVisibility();
+                            }
+                        }
+                    }
+                }
+            } finally {
+                finishInputEvent(event, false /* handled */);
+            }
+        }
+    }
+
+    /**
+     * Called when layout of the windows is about to start.
+     *
+     * @param displayFrames frames of the display we are doing layout on.
+     * @param uiMode The current uiMode in configuration.
+     */
+    public void beginLayoutLw(DisplayFrames displayFrames, int uiMode) {
+        displayFrames.onBeginLayout();
+        mSystemGestures.screenWidth = displayFrames.mUnrestricted.width();
+        mSystemGestures.screenHeight = displayFrames.mUnrestricted.height();
+
+        // For purposes of putting out fake window up to steal focus, we will
+        // drive nav being hidden only by whether it is requested.
+        final int sysui = mLastSystemUiFlags;
+        boolean navVisible = (sysui & View.SYSTEM_UI_FLAG_HIDE_NAVIGATION) == 0;
+        boolean navTranslucent = (sysui
+                & (View.NAVIGATION_BAR_TRANSLUCENT | View.NAVIGATION_BAR_TRANSPARENT)) != 0;
+        boolean immersive = (sysui & View.SYSTEM_UI_FLAG_IMMERSIVE) != 0;
+        boolean immersiveSticky = (sysui & View.SYSTEM_UI_FLAG_IMMERSIVE_STICKY) != 0;
+        boolean navAllowedHidden = immersive || immersiveSticky;
+        navTranslucent &= !immersiveSticky;  // transient trumps translucent
+        boolean isKeyguardShowing = isStatusBarKeyguard()
+                && !mService.mPolicy.isKeyguardOccluded();
+        if (!isKeyguardShowing) {
+            navTranslucent &= areTranslucentBarsAllowed();
+        }
+        boolean statusBarForcesShowingNavigation = !isKeyguardShowing && mStatusBar != null
+                && (mStatusBar.getAttrs().privateFlags
+                & PRIVATE_FLAG_STATUS_FORCE_SHOW_NAVIGATION) != 0;
+
+        // When the navigation bar isn't visible, we put up a fake input window to catch all
+        // touch events. This way we can detect when the user presses anywhere to bring back the
+        // nav bar and ensure the application doesn't see the event.
+        if (navVisible || navAllowedHidden) {
+            if (mInputConsumer != null) {
+                mHandler.sendMessage(
+                        mHandler.obtainMessage(MSG_DISPOSE_INPUT_CONSUMER, mInputConsumer));
+                mInputConsumer = null;
+            }
+        } else if (mInputConsumer == null && mStatusBar != null && canHideNavigationBar()) {
+            mInputConsumer = mService.createInputConsumer(mHandler.getLooper(),
+                    INPUT_CONSUMER_NAVIGATION,
+                    HideNavInputEventReceiver::new,
+                    displayFrames.mDisplayId);
+            // As long as mInputConsumer is active, hover events are not dispatched to the app
+            // and the pointer icon is likely to become stale. Hide it to avoid confusion.
+            InputManager.getInstance().setPointerIconType(PointerIcon.TYPE_NULL);
+        }
+
+        // For purposes of positioning and showing the nav bar, if we have decided that it can't
+        // be hidden (because of the screen aspect ratio), then take that into account.
+        navVisible |= !canHideNavigationBar();
+
+        boolean updateSysUiVisibility = layoutNavigationBar(displayFrames, uiMode, navVisible,
+                navTranslucent, navAllowedHidden, statusBarForcesShowingNavigation);
+        if (DEBUG_LAYOUT) Slog.i(TAG, "mDock rect:" + displayFrames.mDock);
+        updateSysUiVisibility |= layoutStatusBar(displayFrames, sysui, isKeyguardShowing);
+        if (updateSysUiVisibility) {
+            updateSystemUiVisibilityLw();
+        }
+        layoutScreenDecorWindows(displayFrames);
+
+        if (displayFrames.mDisplayCutoutSafe.top > displayFrames.mUnrestricted.top) {
+            // Make sure that the zone we're avoiding for the cutout is at least as tall as the
+            // status bar; otherwise fullscreen apps will end up cutting halfway into the status
+            // bar.
+            displayFrames.mDisplayCutoutSafe.top = Math.max(displayFrames.mDisplayCutoutSafe.top,
+                    displayFrames.mStable.top);
+        }
+    }
+
+    private void layoutScreenDecorWindows(DisplayFrames displayFrames) {
+        if (mScreenDecorWindows.isEmpty()) {
+            return;
+        }
+
+        sTmpRect.setEmpty();
+        sTmpDockedFrame.set(displayFrames.mDock);
+
+        final int displayId = displayFrames.mDisplayId;
+        final Rect dockFrame = displayFrames.mDock;
+        final int displayHeight = displayFrames.mDisplayHeight;
+        final int displayWidth = displayFrames.mDisplayWidth;
+
+        for (int i = mScreenDecorWindows.size() - 1; i >= 0; --i) {
+            final WindowState w = mScreenDecorWindows.valueAt(i);
+            if (w.getDisplayId() != displayId || !w.isVisibleLw()) {
+                // Skip if not on the same display or not visible.
+                continue;
+            }
+
+            w.getWindowFrames().setFrames(sTmpDockedFrame /* parentFrame */,
+                    sTmpDockedFrame /* displayFrame */, sTmpDockedFrame /* overscanFrame */,
+                    sTmpDockedFrame /* contentFrame */, sTmpDockedFrame /* visibleFrame */,
+                    sTmpRect /* decorFrame */, sTmpDockedFrame /* stableFrame */,
+                    sTmpDockedFrame /* outsetFrame */);
+            w.getWindowFrames().setDisplayCutout(displayFrames.mDisplayCutout);
+            w.computeFrameLw();
+            final Rect frame = w.getFrameLw();
+
+            if (frame.left <= 0 && frame.top <= 0) {
+                // Docked at left or top.
+                if (frame.bottom >= displayHeight) {
+                    // Docked left.
+                    dockFrame.left = Math.max(frame.right, dockFrame.left);
+                } else if (frame.right >= displayWidth) {
+                    // Docked top.
+                    dockFrame.top = Math.max(frame.bottom, dockFrame.top);
+                } else {
+                    Slog.w(TAG, "layoutScreenDecorWindows: Ignoring decor win=" + w
+                            + " not docked on left or top of display. frame=" + frame
+                            + " displayWidth=" + displayWidth + " displayHeight=" + displayHeight);
+                }
+            } else if (frame.right >= displayWidth && frame.bottom >= displayHeight) {
+                // Docked at right or bottom.
+                if (frame.top <= 0) {
+                    // Docked right.
+                    dockFrame.right = Math.min(frame.left, dockFrame.right);
+                } else if (frame.left <= 0) {
+                    // Docked bottom.
+                    dockFrame.bottom = Math.min(frame.top, dockFrame.bottom);
+                } else {
+                    Slog.w(TAG, "layoutScreenDecorWindows: Ignoring decor win=" + w
+                            + " not docked on right or bottom" + " of display. frame=" + frame
+                            + " displayWidth=" + displayWidth + " displayHeight=" + displayHeight);
+                }
+            } else {
+                // Screen decor windows are required to be docked on one of the sides of the screen.
+                Slog.w(TAG, "layoutScreenDecorWindows: Ignoring decor win=" + w
+                        + " not docked on one of the sides of the display. frame=" + frame
+                        + " displayWidth=" + displayWidth + " displayHeight=" + displayHeight);
+            }
+        }
+
+        displayFrames.mRestricted.set(dockFrame);
+        displayFrames.mCurrent.set(dockFrame);
+        displayFrames.mVoiceContent.set(dockFrame);
+        displayFrames.mSystem.set(dockFrame);
+        displayFrames.mContent.set(dockFrame);
+        displayFrames.mRestrictedOverscan.set(dockFrame);
+    }
+
+    private boolean layoutStatusBar(DisplayFrames displayFrames, int sysui,
+            boolean isKeyguardShowing) {
+        // decide where the status bar goes ahead of time
+        if (mStatusBar == null) {
+            return false;
+        }
+        // apply any navigation bar insets
+        sTmpRect.setEmpty();
+        mStatusBar.getWindowFrames().setFrames(displayFrames.mUnrestricted /* parentFrame */,
+                displayFrames.mUnrestricted /* displayFrame */,
+                displayFrames.mStable /* overscanFrame */, displayFrames.mStable /* contentFrame */,
+                displayFrames.mStable /* visibleFrame */, sTmpRect /* decorFrame */,
+                displayFrames.mStable /* stableFrame */, displayFrames.mStable /* outsetFrame */);
+        mStatusBar.getWindowFrames().setDisplayCutout(displayFrames.mDisplayCutout);
+
+        // Let the status bar determine its size.
+        mStatusBar.computeFrameLw();
+
+        // For layout, the status bar is always at the top with our fixed height.
+        displayFrames.mStable.top = displayFrames.mUnrestricted.top
+                + mStatusBarHeightForRotation[displayFrames.mRotation];
+        // Make sure the status bar covers the entire cutout height
+        displayFrames.mStable.top = Math.max(displayFrames.mStable.top,
+                displayFrames.mDisplayCutoutSafe.top);
+
+        // Tell the bar controller where the collapsed status bar content is
+        sTmpRect.set(mStatusBar.getContentFrameLw());
+        sTmpRect.intersect(displayFrames.mDisplayCutoutSafe);
+        sTmpRect.top = mStatusBar.getContentFrameLw().top;  // Ignore top display cutout inset
+        sTmpRect.bottom = displayFrames.mStable.top;  // Use collapsed status bar size
+        mStatusBarController.setContentFrame(sTmpRect);
+
+        boolean statusBarTransient = (sysui & View.STATUS_BAR_TRANSIENT) != 0;
+        boolean statusBarTranslucent = (sysui
+                & (View.STATUS_BAR_TRANSLUCENT | View.STATUS_BAR_TRANSPARENT)) != 0;
+        if (!isKeyguardShowing) {
+            statusBarTranslucent &= areTranslucentBarsAllowed();
+        }
+
+        // If the status bar is hidden, we don't want to cause windows behind it to scroll.
+        if (mStatusBar.isVisibleLw() && !statusBarTransient) {
+            // Status bar may go away, so the screen area it occupies is available to apps but just
+            // covering them when the status bar is visible.
+            final Rect dockFrame = displayFrames.mDock;
+            dockFrame.top = displayFrames.mStable.top;
+            displayFrames.mContent.set(dockFrame);
+            displayFrames.mVoiceContent.set(dockFrame);
+            displayFrames.mCurrent.set(dockFrame);
+
+            if (DEBUG_LAYOUT) Slog.v(TAG, "Status bar: " + String.format(
+                    "dock=%s content=%s cur=%s", dockFrame.toString(),
+                    displayFrames.mContent.toString(), displayFrames.mCurrent.toString()));
+
+            if (!mStatusBar.isAnimatingLw() && !statusBarTranslucent
+                    && !mStatusBarController.wasRecentlyTranslucent()) {
+                // If the opaque status bar is currently requested to be visible, and not in the
+                // process of animating on or off, then we can tell the app that it is covered by
+                // it.
+                displayFrames.mSystem.top = displayFrames.mStable.top;
+            }
+        }
+        return mStatusBarController.checkHiddenLw();
+    }
+
+    private boolean layoutNavigationBar(DisplayFrames displayFrames, int uiMode, boolean navVisible,
+            boolean navTranslucent, boolean navAllowedHidden,
+            boolean statusBarForcesShowingNavigation) {
+        if (mNavigationBar == null) {
+            return false;
+        }
+
+        final Rect navigationFrame = sTmpNavFrame;
+        boolean transientNavBarShowing = mNavigationBarController.isTransientShowing();
+        // Force the navigation bar to its appropriate place and size. We need to do this directly,
+        // instead of relying on it to bubble up from the nav bar, because this needs to change
+        // atomically with screen rotations.
+        final int rotation = displayFrames.mRotation;
+        final int displayHeight = displayFrames.mDisplayHeight;
+        final int displayWidth = displayFrames.mDisplayWidth;
+        final Rect dockFrame = displayFrames.mDock;
+        mNavigationBarPosition = navigationBarPosition(displayWidth, displayHeight, rotation);
+
+        final Rect cutoutSafeUnrestricted = sTmpRect;
+        cutoutSafeUnrestricted.set(displayFrames.mUnrestricted);
+        cutoutSafeUnrestricted.intersectUnchecked(displayFrames.mDisplayCutoutSafe);
+
+        if (mNavigationBarPosition == NAV_BAR_BOTTOM) {
+            // It's a system nav bar or a portrait screen; nav bar goes on bottom.
+            final int top = cutoutSafeUnrestricted.bottom
+                    - getNavigationBarHeight(rotation, uiMode);
+            // EXPERIMENT TODO(b/113952590): Remove once experiment in bug is completed
+            final int topNavBar = cutoutSafeUnrestricted.bottom
+                    - mExperiments.getNavigationBarFrameHeight();
+            navigationFrame.set(0, topNavBar, displayWidth, displayFrames.mUnrestricted.bottom);
+            // EXPERIMENT END
+            displayFrames.mStable.bottom = displayFrames.mStableFullscreen.bottom = top;
+            if (transientNavBarShowing) {
+                mNavigationBarController.setBarShowingLw(true);
+            } else if (navVisible) {
+                mNavigationBarController.setBarShowingLw(true);
+                dockFrame.bottom = displayFrames.mRestricted.bottom =
+                        displayFrames.mRestrictedOverscan.bottom = top;
+            } else {
+                // We currently want to hide the navigation UI - unless we expanded the status bar.
+                mNavigationBarController.setBarShowingLw(statusBarForcesShowingNavigation);
+            }
+            if (navVisible && !navTranslucent && !navAllowedHidden
+                    && !mNavigationBar.isAnimatingLw()
+                    && !mNavigationBarController.wasRecentlyTranslucent()) {
+                // If the opaque nav bar is currently requested to be visible and not in the process
+                // of animating on or off, then we can tell the app that it is covered by it.
+                displayFrames.mSystem.bottom = top;
+            }
+        } else if (mNavigationBarPosition == NAV_BAR_RIGHT) {
+            // Landscape screen; nav bar goes to the right.
+            final int left = cutoutSafeUnrestricted.right
+                    - getNavigationBarWidth(rotation, uiMode);
+            // EXPERIMENT TODO(b/113952590): Remove once experiment in bug is completed
+            final int leftNavBar = cutoutSafeUnrestricted.right
+                    - mExperiments.getNavigationBarFrameWidth();
+            navigationFrame.set(leftNavBar, 0, displayFrames.mUnrestricted.right, displayHeight);
+            // EXPERIMENT END
+            displayFrames.mStable.right = displayFrames.mStableFullscreen.right = left;
+            if (transientNavBarShowing) {
+                mNavigationBarController.setBarShowingLw(true);
+            } else if (navVisible) {
+                mNavigationBarController.setBarShowingLw(true);
+                dockFrame.right = displayFrames.mRestricted.right =
+                        displayFrames.mRestrictedOverscan.right = left;
+            } else {
+                // We currently want to hide the navigation UI - unless we expanded the status bar.
+                mNavigationBarController.setBarShowingLw(statusBarForcesShowingNavigation);
+            }
+            if (navVisible && !navTranslucent && !navAllowedHidden
+                    && !mNavigationBar.isAnimatingLw()
+                    && !mNavigationBarController.wasRecentlyTranslucent()) {
+                // If the nav bar is currently requested to be visible, and not in the process of
+                // animating on or off, then we can tell the app that it is covered by it.
+                displayFrames.mSystem.right = left;
+            }
+        } else if (mNavigationBarPosition == NAV_BAR_LEFT) {
+            // Seascape screen; nav bar goes to the left.
+            final int right = cutoutSafeUnrestricted.left
+                    + getNavigationBarWidth(rotation, uiMode);
+            // EXPERIMENT TODO(b/113952590): Remove once experiment in bug is completed
+            final int rightNavBar = cutoutSafeUnrestricted.left
+                    + mExperiments.getNavigationBarFrameWidth();
+            navigationFrame.set(displayFrames.mUnrestricted.left, 0, rightNavBar, displayHeight);
+            // EXPERIMENT END
+            displayFrames.mStable.left = displayFrames.mStableFullscreen.left = right;
+            if (transientNavBarShowing) {
+                mNavigationBarController.setBarShowingLw(true);
+            } else if (navVisible) {
+                mNavigationBarController.setBarShowingLw(true);
+                dockFrame.left = displayFrames.mRestricted.left =
+                        displayFrames.mRestrictedOverscan.left = right;
+            } else {
+                // We currently want to hide the navigation UI - unless we expanded the status bar.
+                mNavigationBarController.setBarShowingLw(statusBarForcesShowingNavigation);
+            }
+            if (navVisible && !navTranslucent && !navAllowedHidden
+                    && !mNavigationBar.isAnimatingLw()
+                    && !mNavigationBarController.wasRecentlyTranslucent()) {
+                // If the nav bar is currently requested to be visible, and not in the process of
+                // animating on or off, then we can tell the app that it is covered by it.
+                displayFrames.mSystem.left = right;
+            }
+        }
+
+        // Make sure the content and current rectangles are updated to account for the restrictions
+        // from the navigation bar.
+        displayFrames.mCurrent.set(dockFrame);
+        displayFrames.mVoiceContent.set(dockFrame);
+        displayFrames.mContent.set(dockFrame);
+        // And compute the final frame.
+        sTmpRect.setEmpty();
+        mNavigationBar.getWindowFrames().setFrames(navigationFrame /* parentFrame */,
+                navigationFrame /* displayFrame */, navigationFrame /* overscanFrame */,
+                displayFrames.mDisplayCutoutSafe /* contentFrame */,
+                navigationFrame /* visibleFrame */, sTmpRect /* decorFrame */,
+                navigationFrame /* stableFrame */,
+                displayFrames.mDisplayCutoutSafe /* outsetFrame */);
+        mNavigationBar.getWindowFrames().setDisplayCutout(displayFrames.mDisplayCutout);
+        mNavigationBar.computeFrameLw();
+        mNavigationBarController.setContentFrame(mNavigationBar.getContentFrameLw());
+
+        if (DEBUG_LAYOUT) Slog.i(TAG, "mNavigationBar frame: " + navigationFrame);
+        return mNavigationBarController.checkHiddenLw();
+    }
+
+    private void setAttachedWindowFrames(WindowState win, int fl, int adjust, WindowState attached,
+            boolean insetDecors, Rect pf, Rect df, Rect of, Rect cf, Rect vf,
+            DisplayFrames displayFrames) {
+        if (!win.isInputMethodTarget() && attached.isInputMethodTarget()) {
+            // Here's a special case: if the child window is not the 'dock window'
+            // or input method target, and the window it is attached to is below
+            // the dock window, then the frames we computed for the window it is
+            // attached to can not be used because the dock is effectively part
+            // of the underlying window and the attached window is floating on top
+            // of the whole thing. So, we ignore the attached window and explicitly
+            // compute the frames that would be appropriate without the dock.
+            vf.set(displayFrames.mDock);
+            cf.set(displayFrames.mDock);
+            of.set(displayFrames.mDock);
+            df.set(displayFrames.mDock);
+        } else {
+            // The effective display frame of the attached window depends on whether it is taking
+            // care of insetting its content. If not, we need to use the parent's content frame so
+            // that the entire window is positioned within that content. Otherwise we can use the
+            // overscan frame and let the attached window take care of positioning its content
+            // appropriately.
+            if (adjust != SOFT_INPUT_ADJUST_RESIZE) {
+                // Set the content frame of the attached window to the parent's decor frame
+                // (same as content frame when IME isn't present) if specifically requested by
+                // setting {@link WindowManager.LayoutParams#FLAG_LAYOUT_ATTACHED_IN_DECOR} flag.
+                // Otherwise, use the overscan frame.
+                cf.set((fl & FLAG_LAYOUT_ATTACHED_IN_DECOR) != 0
+                        ? attached.getContentFrameLw() : attached.getOverscanFrameLw());
+            } else {
+                // If the window is resizing, then we want to base the content frame on our attached
+                // content frame to resize...however, things can be tricky if the attached window is
+                // NOT in resize mode, in which case its content frame will be larger.
+                // Ungh. So to deal with that, make sure the content frame we end up using is not
+                // covering the IM dock.
+                cf.set(attached.getContentFrameLw());
+                if (attached.isVoiceInteraction()) {
+                    cf.intersectUnchecked(displayFrames.mVoiceContent);
+                } else if (win.isInputMethodTarget() || attached.isInputMethodTarget()) {
+                    cf.intersectUnchecked(displayFrames.mContent);
+                }
+            }
+            df.set(insetDecors ? attached.getDisplayFrameLw() : cf);
+            of.set(insetDecors ? attached.getOverscanFrameLw() : cf);
+            vf.set(attached.getVisibleFrameLw());
+        }
+        // The LAYOUT_IN_SCREEN flag is used to determine whether the attached window should be
+        // positioned relative to its parent or the entire screen.
+        pf.set((fl & FLAG_LAYOUT_IN_SCREEN) == 0 ? attached.getFrameLw() : df);
+    }
+
+    private void applyStableConstraints(int sysui, int fl, Rect r, DisplayFrames displayFrames) {
+        if ((sysui & View.SYSTEM_UI_FLAG_LAYOUT_STABLE) == 0) {
+            return;
+        }
+        // If app is requesting a stable layout, don't let the content insets go below the stable
+        // values.
+        if ((fl & FLAG_FULLSCREEN) != 0) {
+            r.intersectUnchecked(displayFrames.mStableFullscreen);
+        } else {
+            r.intersectUnchecked(displayFrames.mStable);
+        }
+    }
+
+    private boolean canReceiveInput(WindowState win) {
+        boolean notFocusable =
+                (win.getAttrs().flags & WindowManager.LayoutParams.FLAG_NOT_FOCUSABLE) != 0;
+        boolean altFocusableIm =
+                (win.getAttrs().flags & WindowManager.LayoutParams.FLAG_ALT_FOCUSABLE_IM) != 0;
+        boolean notFocusableForIm = notFocusable ^ altFocusableIm;
+        return !notFocusableForIm;
+    }
+
+    /**
+     * Called for each window attached to the window manager as layout is proceeding. The
+     * implementation of this function must take care of setting the window's frame, either here or
+     * in finishLayout().
+     *
+     * @param win The window being positioned.
+     * @param attached For sub-windows, the window it is attached to; this
+     *                 window will already have had layoutWindow() called on it
+     *                 so you can use its Rect.  Otherwise null.
+     * @param displayFrames The display frames.
+     */
+    public void layoutWindowLw(WindowState win, WindowState attached, DisplayFrames displayFrames) {
+        // We've already done the navigation bar, status bar, and all screen decor windows. If the
+        // status bar can receive input, we need to layout it again to accommodate for the IME
+        // window.
+        if ((win == mStatusBar && !canReceiveInput(win)) || win == mNavigationBar
+                || mScreenDecorWindows.contains(win)) {
+            return;
+        }
+        final WindowManager.LayoutParams attrs = win.getAttrs();
+        final boolean isDefaultDisplay = win.isDefaultDisplay();
+
+        final int type = attrs.type;
+        final int fl = PolicyControl.getWindowFlags(win, attrs);
+        final int pfl = attrs.privateFlags;
+        final int sim = attrs.softInputMode;
+        final int requestedSysUiFl = PolicyControl.getSystemUiVisibility(null, attrs);
+        final int sysUiFl = requestedSysUiFl | getImpliedSysUiFlagsForLayout(attrs);
+
+        final WindowFrames windowFrames = win.getWindowFrames();
+
+        windowFrames.setHasOutsets(false);
+        sTmpLastParentFrame.set(windowFrames.mParentFrame);
+        final Rect pf = windowFrames.mParentFrame;
+        final Rect df = windowFrames.mDisplayFrame;
+        final Rect of = windowFrames.mOverscanFrame;
+        final Rect cf = windowFrames.mContentFrame;
+        final Rect vf = windowFrames.mVisibleFrame;
+        final Rect dcf = windowFrames.mDecorFrame;
+        final Rect sf = windowFrames.mStableFrame;
+        dcf.setEmpty();
+        windowFrames.setParentFrameWasClippedByDisplayCutout(false);
+        windowFrames.setDisplayCutout(displayFrames.mDisplayCutout);
+
+        final boolean hasNavBar = hasNavigationBar() && mNavigationBar != null
+                && mNavigationBar.isVisibleLw();
+
+        final int adjust = sim & SOFT_INPUT_MASK_ADJUST;
+
+        final boolean requestedFullscreen = (fl & FLAG_FULLSCREEN) != 0
+                || (requestedSysUiFl & View.SYSTEM_UI_FLAG_FULLSCREEN) != 0;
+
+        final boolean layoutInScreen = (fl & FLAG_LAYOUT_IN_SCREEN) == FLAG_LAYOUT_IN_SCREEN;
+        final boolean layoutInsetDecor = (fl & FLAG_LAYOUT_INSET_DECOR) == FLAG_LAYOUT_INSET_DECOR;
+
+        sf.set(displayFrames.mStable);
+
+        if (type == TYPE_INPUT_METHOD) {
+            vf.set(displayFrames.mDock);
+            cf.set(displayFrames.mDock);
+            of.set(displayFrames.mDock);
+            df.set(displayFrames.mDock);
+            windowFrames.mParentFrame.set(displayFrames.mDock);
+            // IM dock windows layout below the nav bar...
+            pf.bottom = df.bottom = of.bottom = displayFrames.mUnrestricted.bottom;
+            // ...with content insets above the nav bar
+            cf.bottom = vf.bottom = displayFrames.mStable.bottom;
+            if (mStatusBar != null && mFocusedWindow == mStatusBar && canReceiveInput(mStatusBar)) {
+                // The status bar forces the navigation bar while it's visible. Make sure the IME
+                // avoids the navigation bar in that case.
+                if (mNavigationBarPosition == NAV_BAR_RIGHT) {
+                    pf.right = df.right = of.right = cf.right = vf.right =
+                            displayFrames.mStable.right;
+                } else if (mNavigationBarPosition == NAV_BAR_LEFT) {
+                    pf.left = df.left = of.left = cf.left = vf.left = displayFrames.mStable.left;
+                }
+            }
+
+            // EXPERIMENT TODO(b/113952590): Remove once experiment in bug is completed
+            // Offset the ime to avoid overlapping with the nav bar
+            mExperiments.offsetWindowFramesForNavBar(mNavigationBarPosition, win);
+            // EXPERIMENT END
+
+            // IM dock windows always go to the bottom of the screen.
+            attrs.gravity = Gravity.BOTTOM;
+        } else if (type == TYPE_VOICE_INTERACTION) {
+            of.set(displayFrames.mUnrestricted);
+            df.set(displayFrames.mUnrestricted);
+            pf.set(displayFrames.mUnrestricted);
+            if (adjust != SOFT_INPUT_ADJUST_RESIZE) {
+                cf.set(displayFrames.mDock);
+            } else {
+                cf.set(displayFrames.mContent);
+            }
+            if (adjust != SOFT_INPUT_ADJUST_NOTHING) {
+                vf.set(displayFrames.mCurrent);
+            } else {
+                vf.set(cf);
+            }
+        } else if (type == TYPE_WALLPAPER) {
+            layoutWallpaper(displayFrames, pf, df, of, cf);
+        } else if (win == mStatusBar) {
+            of.set(displayFrames.mUnrestricted);
+            df.set(displayFrames.mUnrestricted);
+            pf.set(displayFrames.mUnrestricted);
+            cf.set(displayFrames.mStable);
+            vf.set(displayFrames.mStable);
+
+            if (adjust == SOFT_INPUT_ADJUST_RESIZE) {
+                cf.bottom = displayFrames.mContent.bottom;
+            } else {
+                cf.bottom = displayFrames.mDock.bottom;
+                vf.bottom = displayFrames.mContent.bottom;
+            }
+        } else {
+            dcf.set(displayFrames.mSystem);
+            final boolean inheritTranslucentDecor =
+                    (attrs.privateFlags & PRIVATE_FLAG_INHERIT_TRANSLUCENT_DECOR) != 0;
+            final boolean isAppWindow =
+                    type >= FIRST_APPLICATION_WINDOW && type <= LAST_APPLICATION_WINDOW;
+            final boolean topAtRest =
+                    win == mTopFullscreenOpaqueWindowState && !win.isAnimatingLw();
+            if (isAppWindow && !inheritTranslucentDecor && !topAtRest) {
+                if ((sysUiFl & View.SYSTEM_UI_FLAG_FULLSCREEN) == 0
+                        && (fl & FLAG_FULLSCREEN) == 0
+                        && (fl & FLAG_TRANSLUCENT_STATUS) == 0
+                        && (fl & FLAG_DRAWS_SYSTEM_BAR_BACKGROUNDS) == 0
+                        && (pfl & PRIVATE_FLAG_FORCE_DRAW_STATUS_BAR_BACKGROUND) == 0) {
+                    // Ensure policy decor includes status bar
+                    dcf.top = displayFrames.mStable.top;
+                }
+                if ((fl & FLAG_TRANSLUCENT_NAVIGATION) == 0
+                        && (sysUiFl & View.SYSTEM_UI_FLAG_HIDE_NAVIGATION) == 0
+                        && (fl & FLAG_DRAWS_SYSTEM_BAR_BACKGROUNDS) == 0) {
+                    // Ensure policy decor includes navigation bar
+                    dcf.bottom = displayFrames.mStable.bottom;
+                    dcf.right = displayFrames.mStable.right;
+                }
+            }
+
+            if (layoutInScreen && layoutInsetDecor) {
+                if (DEBUG_LAYOUT) Slog.v(TAG, "layoutWindowLw(" + attrs.getTitle()
+                        + "): IN_SCREEN, INSET_DECOR");
+                // This is the case for a normal activity window: we want it to cover all of the
+                // screen space, and it can take care of moving its contents to account for screen
+                // decorations that intrude into that space.
+                if (attached != null) {
+                    // If this window is attached to another, our display
+                    // frame is the same as the one we are attached to.
+                    setAttachedWindowFrames(win, fl, adjust, attached, true, pf, df, of, cf, vf,
+                            displayFrames);
+                } else {
+                    if (type == TYPE_STATUS_BAR_PANEL || type == TYPE_STATUS_BAR_SUB_PANEL) {
+                        // Status bar panels are the only windows who can go on top of the status
+                        // bar. They are protected by the STATUS_BAR_SERVICE permission, so they
+                        // have the same privileges as the status bar itself.
+                        //
+                        // However, they should still dodge the navigation bar if it exists.
+
+                        pf.left = df.left = of.left = hasNavBar
+                                ? displayFrames.mDock.left : displayFrames.mUnrestricted.left;
+                        pf.top = df.top = of.top = displayFrames.mUnrestricted.top;
+                        pf.right = df.right = of.right = hasNavBar
+                                ? displayFrames.mRestricted.right
+                                : displayFrames.mUnrestricted.right;
+                        pf.bottom = df.bottom = of.bottom = hasNavBar
+                                ? displayFrames.mRestricted.bottom
+                                : displayFrames.mUnrestricted.bottom;
+
+                        if (DEBUG_LAYOUT) Slog.v(TAG, "Laying out status bar window: " + pf);
+                    } else if ((fl & FLAG_LAYOUT_IN_OVERSCAN) != 0
+                            && type >= FIRST_APPLICATION_WINDOW && type <= LAST_SUB_WINDOW) {
+                        // Asking to layout into the overscan region, so give it that pure
+                        // unrestricted area.
+                        of.set(displayFrames.mOverscan);
+                        df.set(displayFrames.mOverscan);
+                        pf.set(displayFrames.mOverscan);
+                    } else if ((sysUiFl & View.SYSTEM_UI_FLAG_LAYOUT_HIDE_NAVIGATION) != 0
+                            && (type >= FIRST_APPLICATION_WINDOW && type <= LAST_SUB_WINDOW
+                            || type == TYPE_VOLUME_OVERLAY)) {
+                        // Asking for layout as if the nav bar is hidden, lets the application
+                        // extend into the unrestricted overscan screen area. We only do this for
+                        // application windows and certain system windows to ensure no window that
+                        // can be above the nav bar can do this.
+                        df.set(displayFrames.mOverscan);
+                        pf.set(displayFrames.mOverscan);
+                        // We need to tell the app about where the frame inside the overscan is, so
+                        // it can inset its content by that amount -- it didn't ask to actually
+                        // extend itself into the overscan region.
+                        of.set(displayFrames.mUnrestricted);
+                    } else {
+                        df.set(displayFrames.mRestrictedOverscan);
+                        pf.set(displayFrames.mRestrictedOverscan);
+                        // We need to tell the app about where the frame inside the overscan
+                        // is, so it can inset its content by that amount -- it didn't ask
+                        // to actually extend itself into the overscan region.
+                        of.set(displayFrames.mUnrestricted);
+                    }
+
+                    if ((fl & FLAG_FULLSCREEN) == 0) {
+                        if (win.isVoiceInteraction()) {
+                            cf.set(displayFrames.mVoiceContent);
+                        } else {
+                            if (adjust != SOFT_INPUT_ADJUST_RESIZE) {
+                                cf.set(displayFrames.mDock);
+                            } else {
+                                cf.set(displayFrames.mContent);
+                            }
+                        }
+                    } else {
+                        // Full screen windows are always given a layout that is as if the status
+                        // bar and other transient decors are gone. This is to avoid bad states when
+                        // moving from a window that is not hiding the status bar to one that is.
+                        cf.set(displayFrames.mRestricted);
+                    }
+                    applyStableConstraints(sysUiFl, fl, cf, displayFrames);
+                    if (adjust != SOFT_INPUT_ADJUST_NOTHING) {
+                        vf.set(displayFrames.mCurrent);
+                    } else {
+                        vf.set(cf);
+                    }
+
+                    // EXPERIMENT TODO(b/113952590): Remove once experiment in bug is completed
+                    mExperiments.offsetWindowFramesForNavBar(mNavigationBarPosition, win);
+                    // EXPERIMENT END
+                }
+            } else if (layoutInScreen || (sysUiFl
+                    & (View.SYSTEM_UI_FLAG_LAYOUT_FULLSCREEN
+                    | View.SYSTEM_UI_FLAG_LAYOUT_HIDE_NAVIGATION)) != 0) {
+                if (DEBUG_LAYOUT) Slog.v(TAG, "layoutWindowLw(" + attrs.getTitle()
+                        + "): IN_SCREEN");
+                // A window that has requested to fill the entire screen just
+                // gets everything, period.
+                if (type == TYPE_STATUS_BAR_PANEL || type == TYPE_STATUS_BAR_SUB_PANEL) {
+                    cf.set(displayFrames.mUnrestricted);
+                    of.set(displayFrames.mUnrestricted);
+                    df.set(displayFrames.mUnrestricted);
+                    pf.set(displayFrames.mUnrestricted);
+                    if (hasNavBar) {
+                        pf.left = df.left = of.left = cf.left = displayFrames.mDock.left;
+                        pf.right = df.right = of.right = cf.right = displayFrames.mRestricted.right;
+                        pf.bottom = df.bottom = of.bottom = cf.bottom =
+                                displayFrames.mRestricted.bottom;
+                    }
+                    if (DEBUG_LAYOUT) Slog.v(TAG, "Laying out IN_SCREEN status bar window: " + pf);
+                } else if (type == TYPE_NAVIGATION_BAR || type == TYPE_NAVIGATION_BAR_PANEL) {
+                    // The navigation bar has Real Ultimate Power.
+                    of.set(displayFrames.mUnrestricted);
+                    df.set(displayFrames.mUnrestricted);
+                    pf.set(displayFrames.mUnrestricted);
+                    if (DEBUG_LAYOUT) Slog.v(TAG, "Laying out navigation bar window: " + pf);
+                } else if ((type == TYPE_SECURE_SYSTEM_OVERLAY || type == TYPE_SCREENSHOT)
+                        && ((fl & FLAG_FULLSCREEN) != 0)) {
+                    // Fullscreen secure system overlays get what they ask for. Screenshot region
+                    // selection overlay should also expand to full screen.
+                    cf.set(displayFrames.mOverscan);
+                    of.set(displayFrames.mOverscan);
+                    df.set(displayFrames.mOverscan);
+                    pf.set(displayFrames.mOverscan);
+                } else if (type == TYPE_BOOT_PROGRESS) {
+                    // Boot progress screen always covers entire display.
+                    cf.set(displayFrames.mOverscan);
+                    of.set(displayFrames.mOverscan);
+                    df.set(displayFrames.mOverscan);
+                    pf.set(displayFrames.mOverscan);
+                } else if ((fl & FLAG_LAYOUT_IN_OVERSCAN) != 0
+                        && type >= FIRST_APPLICATION_WINDOW && type <= LAST_SUB_WINDOW) {
+                    // Asking to layout into the overscan region, so give it that pure unrestricted
+                    // area.
+                    cf.set(displayFrames.mOverscan);
+                    of.set(displayFrames.mOverscan);
+                    df.set(displayFrames.mOverscan);
+                    pf.set(displayFrames.mOverscan);
+                } else if ((sysUiFl & View.SYSTEM_UI_FLAG_LAYOUT_HIDE_NAVIGATION) != 0
+                        && (type == TYPE_STATUS_BAR
+                        || type == TYPE_TOAST
+                        || type == TYPE_DOCK_DIVIDER
+                        || type == TYPE_VOICE_INTERACTION_STARTING
+                        || (type >= FIRST_APPLICATION_WINDOW && type <= LAST_SUB_WINDOW))) {
+                    // Asking for layout as if the nav bar is hidden, lets the
+                    // application extend into the unrestricted screen area.  We
+                    // only do this for application windows (or toasts) to ensure no window that
+                    // can be above the nav bar can do this.
+                    // XXX This assumes that an app asking for this will also
+                    // ask for layout in only content.  We can't currently figure out
+                    // what the screen would be if only laying out to hide the nav bar.
+                    cf.set(displayFrames.mUnrestricted);
+                    of.set(displayFrames.mUnrestricted);
+                    df.set(displayFrames.mUnrestricted);
+                    pf.set(displayFrames.mUnrestricted);
+                } else if ((sysUiFl & View.SYSTEM_UI_FLAG_LAYOUT_FULLSCREEN) != 0) {
+                    of.set(displayFrames.mRestricted);
+                    df.set(displayFrames.mRestricted);
+                    pf.set(displayFrames.mRestricted);
+                    if (adjust != SOFT_INPUT_ADJUST_RESIZE) {
+                        cf.set(displayFrames.mDock);
+                    } else {
+                        cf.set(displayFrames.mContent);
+                    }
+                } else {
+                    cf.set(displayFrames.mRestricted);
+                    of.set(displayFrames.mRestricted);
+                    df.set(displayFrames.mRestricted);
+                    pf.set(displayFrames.mRestricted);
+                }
+
+                applyStableConstraints(sysUiFl, fl, cf, displayFrames);
+
+                if (adjust != SOFT_INPUT_ADJUST_NOTHING) {
+                    vf.set(displayFrames.mCurrent);
+                } else {
+                    vf.set(cf);
+                }
+            } else if (attached != null) {
+                if (DEBUG_LAYOUT) Slog.v(TAG, "layoutWindowLw(" + attrs.getTitle()
+                        + "): attached to " + attached);
+                // A child window should be placed inside of the same visible
+                // frame that its parent had.
+                setAttachedWindowFrames(win, fl, adjust, attached, false, pf, df, of, cf, vf,
+                        displayFrames);
+            } else {
+                if (DEBUG_LAYOUT) Slog.v(TAG, "layoutWindowLw(" + attrs.getTitle()
+                        + "): normal window");
+                // Otherwise, a normal window must be placed inside the content
+                // of all screen decorations.
+                if (type == TYPE_STATUS_BAR_PANEL) {
+                    // Status bar panels can go on
+                    // top of the status bar. They are protected by the STATUS_BAR_SERVICE
+                    // permission, so they have the same privileges as the status bar itself.
+                    cf.set(displayFrames.mRestricted);
+                    of.set(displayFrames.mRestricted);
+                    df.set(displayFrames.mRestricted);
+                    pf.set(displayFrames.mRestricted);
+                } else if (type == TYPE_TOAST || type == TYPE_SYSTEM_ALERT) {
+                    // These dialogs are stable to interim decor changes.
+                    cf.set(displayFrames.mStable);
+                    of.set(displayFrames.mStable);
+                    df.set(displayFrames.mStable);
+                    pf.set(displayFrames.mStable);
+                } else {
+                    pf.set(displayFrames.mContent);
+                    if (win.isVoiceInteraction()) {
+                        cf.set(displayFrames.mVoiceContent);
+                        of.set(displayFrames.mVoiceContent);
+                        df.set(displayFrames.mVoiceContent);
+                    } else if (adjust != SOFT_INPUT_ADJUST_RESIZE) {
+                        cf.set(displayFrames.mDock);
+                        of.set(displayFrames.mDock);
+                        df.set(displayFrames.mDock);
+                    } else {
+                        cf.set(displayFrames.mContent);
+                        of.set(displayFrames.mContent);
+                        df.set(displayFrames.mContent);
+                    }
+                    if (adjust != SOFT_INPUT_ADJUST_NOTHING) {
+                        vf.set(displayFrames.mCurrent);
+                    } else {
+                        vf.set(cf);
+                    }
+                }
+            }
+        }
+
+        final int cutoutMode = attrs.layoutInDisplayCutoutMode;
+        final boolean attachedInParent = attached != null && !layoutInScreen;
+        final boolean requestedHideNavigation =
+                (requestedSysUiFl & View.SYSTEM_UI_FLAG_HIDE_NAVIGATION) != 0;
+
+        // TYPE_BASE_APPLICATION windows are never considered floating here because they don't get
+        // cropped / shifted to the displayFrame in WindowState.
+        final boolean floatingInScreenWindow = !attrs.isFullscreen() && layoutInScreen
+                && type != TYPE_BASE_APPLICATION;
+
+        // Ensure that windows with a DEFAULT or NEVER display cutout mode are laid out in
+        // the cutout safe zone.
+        if (cutoutMode != LAYOUT_IN_DISPLAY_CUTOUT_MODE_ALWAYS) {
+            final Rect displayCutoutSafeExceptMaybeBars = sTmpDisplayCutoutSafeExceptMaybeBarsRect;
+            displayCutoutSafeExceptMaybeBars.set(displayFrames.mDisplayCutoutSafe);
+            if (layoutInScreen && layoutInsetDecor && !requestedFullscreen
+                    && cutoutMode == LAYOUT_IN_DISPLAY_CUTOUT_MODE_DEFAULT) {
+                // At the top we have the status bar, so apps that are
+                // LAYOUT_IN_SCREEN | LAYOUT_INSET_DECOR but not FULLSCREEN
+                // already expect that there's an inset there and we don't need to exclude
+                // the window from that area.
+                displayCutoutSafeExceptMaybeBars.top = Integer.MIN_VALUE;
+            }
+            if (layoutInScreen && layoutInsetDecor && !requestedHideNavigation
+                    && cutoutMode == LAYOUT_IN_DISPLAY_CUTOUT_MODE_DEFAULT) {
+                // Same for the navigation bar.
+                switch (mNavigationBarPosition) {
+                    case NAV_BAR_BOTTOM:
+                        displayCutoutSafeExceptMaybeBars.bottom = Integer.MAX_VALUE;
+                        break;
+                    case NAV_BAR_RIGHT:
+                        displayCutoutSafeExceptMaybeBars.right = Integer.MAX_VALUE;
+                        break;
+                    case NAV_BAR_LEFT:
+                        displayCutoutSafeExceptMaybeBars.left = Integer.MIN_VALUE;
+                        break;
+                }
+            }
+            if (type == TYPE_INPUT_METHOD && mNavigationBarPosition == NAV_BAR_BOTTOM) {
+                // The IME can always extend under the bottom cutout if the navbar is there.
+                displayCutoutSafeExceptMaybeBars.bottom = Integer.MAX_VALUE;
+            }
+            // Windows that are attached to a parent and laid out in said parent already avoid
+            // the cutout according to that parent and don't need to be further constrained.
+            // Floating IN_SCREEN windows get what they ask for and lay out in the full screen.
+            // They will later be cropped or shifted using the displayFrame in WindowState,
+            // which prevents overlap with the DisplayCutout.
+            if (!attachedInParent && !floatingInScreenWindow) {
+                sTmpRect.set(pf);
+                pf.intersectUnchecked(displayCutoutSafeExceptMaybeBars);
+                windowFrames.setParentFrameWasClippedByDisplayCutout(!sTmpRect.equals(pf));
+            }
+            // Make sure that NO_LIMITS windows clipped to the display don't extend under the
+            // cutout.
+            df.intersectUnchecked(displayCutoutSafeExceptMaybeBars);
+        }
+
+        // Content should never appear in the cutout.
+        cf.intersectUnchecked(displayFrames.mDisplayCutoutSafe);
+
+        // TYPE_SYSTEM_ERROR is above the NavigationBar so it can't be allowed to extend over it.
+        // Also, we don't allow windows in multi-window mode to extend out of the screen.
+        if ((fl & FLAG_LAYOUT_NO_LIMITS) != 0 && type != TYPE_SYSTEM_ERROR
+                && !win.isInMultiWindowMode()) {
+            df.left = df.top = -10000;
+            df.right = df.bottom = 10000;
+            if (type != TYPE_WALLPAPER) {
+                of.left = of.top = cf.left = cf.top = vf.left = vf.top = -10000;
+                of.right = of.bottom = cf.right = cf.bottom = vf.right = vf.bottom = 10000;
+            }
+        }
+
+        // If the device has a chin (e.g. some watches), a dead area at the bottom of the screen we
+        // need to provide information to the clients that want to pretend that you can draw there.
+        // We only want to apply outsets to certain types of windows. For example, we never want to
+        // apply the outsets to floating dialogs, because they wouldn't make sense there.
+        final boolean useOutsets = shouldUseOutsets(attrs, fl);
+        if (isDefaultDisplay && useOutsets) {
+            final Rect osf = windowFrames.mOutsetFrame;
+            osf.set(cf.left, cf.top, cf.right, cf.bottom);
+            windowFrames.setHasOutsets(true);
+            int outset = ScreenShapeHelper.getWindowOutsetBottomPx(mContext.getResources());
+            if (outset > 0) {
+                int rotation = displayFrames.mRotation;
+                if (rotation == Surface.ROTATION_0) {
+                    osf.bottom += outset;
+                } else if (rotation == Surface.ROTATION_90) {
+                    osf.right += outset;
+                } else if (rotation == Surface.ROTATION_180) {
+                    osf.top -= outset;
+                } else if (rotation == Surface.ROTATION_270) {
+                    osf.left -= outset;
+                }
+                if (DEBUG_LAYOUT) Slog.v(TAG, "applying bottom outset of " + outset
+                        + " with rotation " + rotation + ", result: " + osf);
+            }
+        }
+
+        if (DEBUG_LAYOUT) Slog.v(TAG, "Compute frame " + attrs.getTitle()
+                + ": sim=#" + Integer.toHexString(sim)
+                + " attach=" + attached + " type=" + type
+                + String.format(" flags=0x%08x", fl)
+                + " pf=" + pf.toShortString() + " df=" + df.toShortString()
+                + " of=" + of.toShortString()
+                + " cf=" + cf.toShortString() + " vf=" + vf.toShortString()
+                + " dcf=" + dcf.toShortString()
+                + " sf=" + sf.toShortString()
+                + " osf=" + windowFrames.mOutsetFrame.toShortString() + " " + win);
+
+        if (!sTmpLastParentFrame.equals(pf)) {
+            windowFrames.setContentChanged(true);
+        }
+
+        win.computeFrameLw();
+        // Dock windows carve out the bottom of the screen, so normal windows
+        // can't appear underneath them.
+        if (type == TYPE_INPUT_METHOD && win.isVisibleLw()
+                && !win.getGivenInsetsPendingLw()) {
+            offsetInputMethodWindowLw(win, displayFrames);
+        }
+        if (type == TYPE_VOICE_INTERACTION && win.isVisibleLw()
+                && !win.getGivenInsetsPendingLw()) {
+            offsetVoiceInputWindowLw(win, displayFrames);
+        }
+    }
+
+    private void layoutWallpaper(DisplayFrames displayFrames, Rect pf, Rect df, Rect of, Rect cf) {
+        // The wallpaper has Real Ultimate Power, but we want to tell it about the overscan area.
+        df.set(displayFrames.mOverscan);
+        pf.set(displayFrames.mOverscan);
+        cf.set(displayFrames.mUnrestricted);
+        of.set(displayFrames.mUnrestricted);
+    }
+
+    private void offsetInputMethodWindowLw(WindowState win, DisplayFrames displayFrames) {
+        int top = Math.max(win.getDisplayFrameLw().top, win.getContentFrameLw().top);
+        top += win.getGivenContentInsetsLw().top;
+        displayFrames.mContent.bottom = Math.min(displayFrames.mContent.bottom, top);
+        displayFrames.mVoiceContent.bottom = Math.min(displayFrames.mVoiceContent.bottom, top);
+        top = win.getVisibleFrameLw().top;
+        top += win.getGivenVisibleInsetsLw().top;
+        displayFrames.mCurrent.bottom = Math.min(displayFrames.mCurrent.bottom, top);
+        if (DEBUG_LAYOUT) Slog.v(TAG, "Input method: mDockBottom="
+                + displayFrames.mDock.bottom + " mContentBottom="
+                + displayFrames.mContent.bottom + " mCurBottom=" + displayFrames.mCurrent.bottom);
+    }
+
+    private void offsetVoiceInputWindowLw(WindowState win, DisplayFrames displayFrames) {
+        int top = Math.max(win.getDisplayFrameLw().top, win.getContentFrameLw().top);
+        top += win.getGivenContentInsetsLw().top;
+        displayFrames.mVoiceContent.bottom = Math.min(displayFrames.mVoiceContent.bottom, top);
+    }
+
+    /**
+     * Called following layout of all windows before each window has policy applied.
+     */
+    public void beginPostLayoutPolicyLw() {
+        mTopFullscreenOpaqueWindowState = null;
+        mTopFullscreenOpaqueOrDimmingWindowState = null;
+        mTopDockedOpaqueWindowState = null;
+        mTopDockedOpaqueOrDimmingWindowState = null;
+        mForceStatusBar = false;
+        mForceStatusBarFromKeyguard = false;
+        mForceStatusBarTransparent = false;
+        mForcingShowNavBar = false;
+        mForcingShowNavBarLayer = -1;
+
+        mAllowLockscreenWhenOn = false;
+        mShowingDream = false;
+        mWindowSleepTokenNeeded = false;
+    }
+
+    /**
+     * Called following layout of all window to apply policy to each window.
+     *
+     * @param win The window being positioned.
+     * @param attrs The LayoutParams of the window.
+     * @param attached For sub-windows, the window it is attached to. Otherwise null.
+     */
+    public void applyPostLayoutPolicyLw(WindowState win, WindowManager.LayoutParams attrs,
+            WindowState attached, WindowState imeTarget) {
+        final boolean affectsSystemUi = win.canAffectSystemUiFlags();
+        if (DEBUG_LAYOUT) Slog.i(TAG, "Win " + win + ": affectsSystemUi=" + affectsSystemUi);
+        mService.mPolicy.applyKeyguardPolicyLw(win, imeTarget);
+        final int fl = PolicyControl.getWindowFlags(win, attrs);
+        if (mTopFullscreenOpaqueWindowState == null && affectsSystemUi
+                && attrs.type == TYPE_INPUT_METHOD) {
+            mForcingShowNavBar = true;
+            mForcingShowNavBarLayer = win.getSurfaceLayer();
+        }
+        if (attrs.type == TYPE_STATUS_BAR) {
+            if ((attrs.privateFlags & PRIVATE_FLAG_KEYGUARD) != 0) {
+                mForceStatusBarFromKeyguard = true;
+            }
+            if ((attrs.privateFlags & PRIVATE_FLAG_FORCE_STATUS_BAR_VISIBLE_TRANSPARENT) != 0) {
+                mForceStatusBarTransparent = true;
+            }
+        }
+
+        boolean appWindow = attrs.type >= FIRST_APPLICATION_WINDOW
+                && attrs.type < FIRST_SYSTEM_WINDOW;
+        final int windowingMode = win.getWindowingMode();
+        final boolean inFullScreenOrSplitScreenSecondaryWindowingMode =
+                windowingMode == WINDOWING_MODE_FULLSCREEN
+                        || windowingMode == WINDOWING_MODE_SPLIT_SCREEN_SECONDARY;
+        if (mTopFullscreenOpaqueWindowState == null && affectsSystemUi) {
+            if ((fl & FLAG_FORCE_NOT_FULLSCREEN) != 0) {
+                mForceStatusBar = true;
+            }
+            if (attrs.type == TYPE_DREAM) {
+                // If the lockscreen was showing when the dream started then wait
+                // for the dream to draw before hiding the lockscreen.
+                if (!mDreamingLockscreen
+                        || (win.isVisibleLw() && win.hasDrawnLw())) {
+                    mShowingDream = true;
+                    appWindow = true;
+                }
+            }
+
+            // For app windows that are not attached, we decide if all windows in the app they
+            // represent should be hidden or if we should hide the lockscreen. For attached app
+            // windows we defer the decision to the window it is attached to.
+            if (appWindow && attached == null) {
+                if (attrs.isFullscreen() && inFullScreenOrSplitScreenSecondaryWindowingMode) {
+                    if (DEBUG_LAYOUT) Slog.v(TAG, "Fullscreen window: " + win);
+                    mTopFullscreenOpaqueWindowState = win;
+                    if (mTopFullscreenOpaqueOrDimmingWindowState == null) {
+                        mTopFullscreenOpaqueOrDimmingWindowState = win;
+                    }
+                    if ((fl & FLAG_ALLOW_LOCK_WHILE_SCREEN_ON) != 0) {
+                        mAllowLockscreenWhenOn = true;
+                    }
+                }
+            }
+        }
+
+        // Voice interaction overrides both top fullscreen and top docked.
+        if (affectsSystemUi && win.getAttrs().type == TYPE_VOICE_INTERACTION) {
+            if (mTopFullscreenOpaqueWindowState == null) {
+                mTopFullscreenOpaqueWindowState = win;
+                if (mTopFullscreenOpaqueOrDimmingWindowState == null) {
+                    mTopFullscreenOpaqueOrDimmingWindowState = win;
+                }
+            }
+            if (mTopDockedOpaqueWindowState == null) {
+                mTopDockedOpaqueWindowState = win;
+                if (mTopDockedOpaqueOrDimmingWindowState == null) {
+                    mTopDockedOpaqueOrDimmingWindowState = win;
+                }
+            }
+        }
+
+        // Keep track of the window if it's dimming but not necessarily fullscreen.
+        if (mTopFullscreenOpaqueOrDimmingWindowState == null && affectsSystemUi
+                && win.isDimming() && inFullScreenOrSplitScreenSecondaryWindowingMode) {
+            mTopFullscreenOpaqueOrDimmingWindowState = win;
+        }
+
+        // We need to keep track of the top "fullscreen" opaque window for the docked stack
+        // separately, because both the "real fullscreen" opaque window and the one for the docked
+        // stack can control View.SYSTEM_UI_FLAG_LIGHT_STATUS_BAR.
+        if (mTopDockedOpaqueWindowState == null && affectsSystemUi && appWindow && attached == null
+                && attrs.isFullscreen() && windowingMode == WINDOWING_MODE_SPLIT_SCREEN_PRIMARY) {
+            mTopDockedOpaqueWindowState = win;
+            if (mTopDockedOpaqueOrDimmingWindowState == null) {
+                mTopDockedOpaqueOrDimmingWindowState = win;
+            }
+        }
+
+        // Also keep track of any windows that are dimming but not necessarily fullscreen in the
+        // docked stack.
+        if (mTopDockedOpaqueOrDimmingWindowState == null && affectsSystemUi && win.isDimming()
+                && windowingMode == WINDOWING_MODE_SPLIT_SCREEN_PRIMARY) {
+            mTopDockedOpaqueOrDimmingWindowState = win;
+        }
+
+        // Take note if a window wants to acquire a sleep token.
+        if ((attrs.privateFlags & PRIVATE_FLAG_ACQUIRES_SLEEP_TOKEN) != 0
+                && win.canAcquireSleepToken()) {
+            mWindowSleepTokenNeeded = true;
+        }
+    }
+
+    /**
+     * Called following layout of all windows and after policy has been applied
+     * to each window. If in this function you do
+     * something that may have modified the animation state of another window,
+     * be sure to return non-zero in order to perform another pass through layout.
+     *
+     * @return Return any bit set of
+     *         {@link WindowManagerPolicy#FINISH_LAYOUT_REDO_LAYOUT},
+     *         {@link WindowManagerPolicy#FINISH_LAYOUT_REDO_CONFIG},
+     *         {@link WindowManagerPolicy#FINISH_LAYOUT_REDO_WALLPAPER}, or
+     *         {@link WindowManagerPolicy#FINISH_LAYOUT_REDO_ANIM}.
+     */
+    public int finishPostLayoutPolicyLw() {
+        int changes = 0;
+        boolean topIsFullscreen = false;
+
+        // If we are not currently showing a dream then remember the current
+        // lockscreen state.  We will use this to determine whether the dream
+        // started while the lockscreen was showing and remember this state
+        // while the dream is showing.
+        if (!mShowingDream) {
+            mDreamingLockscreen = mService.mPolicy.isKeyguardShowingAndNotOccluded();
+            if (mDreamingSleepTokenNeeded) {
+                mDreamingSleepTokenNeeded = false;
+                mHandler.obtainMessage(MSG_UPDATE_DREAMING_SLEEP_TOKEN, 0, 1).sendToTarget();
+            }
+        } else {
+            if (!mDreamingSleepTokenNeeded) {
+                mDreamingSleepTokenNeeded = true;
+                mHandler.obtainMessage(MSG_UPDATE_DREAMING_SLEEP_TOKEN, 1, 1).sendToTarget();
+            }
+        }
+
+        if (mStatusBar != null) {
+            if (DEBUG_LAYOUT) Slog.i(TAG, "force=" + mForceStatusBar
+                    + " forcefkg=" + mForceStatusBarFromKeyguard
+                    + " top=" + mTopFullscreenOpaqueWindowState);
+            boolean shouldBeTransparent = mForceStatusBarTransparent
+                    && !mForceStatusBar
+                    && !mForceStatusBarFromKeyguard;
+            if (!shouldBeTransparent) {
+                mStatusBarController.setShowTransparent(false /* transparent */);
+            } else if (!mStatusBar.isVisibleLw()) {
+                mStatusBarController.setShowTransparent(true /* transparent */);
+            }
+
+            boolean statusBarForcesShowingNavigation =
+                    (mStatusBar.getAttrs().privateFlags
+                            & PRIVATE_FLAG_STATUS_FORCE_SHOW_NAVIGATION) != 0;
+            boolean topAppHidesStatusBar = topAppHidesStatusBar();
+            if (mForceStatusBar || mForceStatusBarFromKeyguard || mForceStatusBarTransparent
+                    || statusBarForcesShowingNavigation) {
+                if (DEBUG_LAYOUT) Slog.v(TAG, "Showing status bar: forced");
+                if (mStatusBarController.setBarShowingLw(true)) {
+                    changes |= FINISH_LAYOUT_REDO_LAYOUT;
+                }
+                // Maintain fullscreen layout until incoming animation is complete.
+                topIsFullscreen = mTopIsFullscreen && mStatusBar.isAnimatingLw();
+                // Transient status bar is not allowed if status bar is on lockscreen or status bar
+                // is expecting the navigation keys from the user.
+                if ((mForceStatusBarFromKeyguard || statusBarForcesShowingNavigation)
+                        && mStatusBarController.isTransientShowing()) {
+                    mStatusBarController.updateVisibilityLw(false /*transientAllowed*/,
+                            mLastSystemUiFlags, mLastSystemUiFlags);
+                }
+            } else if (mTopFullscreenOpaqueWindowState != null) {
+                topIsFullscreen = topAppHidesStatusBar;
+                // The subtle difference between the window for mTopFullscreenOpaqueWindowState
+                // and mTopIsFullscreen is that mTopIsFullscreen is set only if the window
+                // has the FLAG_FULLSCREEN set.  Not sure if there is another way that to be the
+                // case though.
+                if (mStatusBarController.isTransientShowing()) {
+                    if (mStatusBarController.setBarShowingLw(true)) {
+                        changes |= FINISH_LAYOUT_REDO_LAYOUT;
+                    }
+                } else if (topIsFullscreen
+                        && !mDisplayContent.isStackVisible(WINDOWING_MODE_FREEFORM)
+                        && !mDisplayContent.isStackVisible(WINDOWING_MODE_SPLIT_SCREEN_PRIMARY)) {
+                    if (DEBUG_LAYOUT) Slog.v(TAG, "** HIDING status bar");
+                    if (mStatusBarController.setBarShowingLw(false)) {
+                        changes |= FINISH_LAYOUT_REDO_LAYOUT;
+                    } else {
+                        if (DEBUG_LAYOUT) Slog.v(TAG, "Status bar already hiding");
+                    }
+                } else {
+                    if (DEBUG_LAYOUT) Slog.v(TAG, "** SHOWING status bar: top is not fullscreen");
+                    if (mStatusBarController.setBarShowingLw(true)) {
+                        changes |= FINISH_LAYOUT_REDO_LAYOUT;
+                    }
+                    topAppHidesStatusBar = false;
+                }
+            }
+            mStatusBarController.setTopAppHidesStatusBar(topAppHidesStatusBar);
+        }
+
+        if (mTopIsFullscreen != topIsFullscreen) {
+            if (!topIsFullscreen) {
+                // Force another layout when status bar becomes fully shown.
+                changes |= FINISH_LAYOUT_REDO_LAYOUT;
+            }
+            mTopIsFullscreen = topIsFullscreen;
+        }
+
+        if ((updateSystemUiVisibilityLw() & SYSTEM_UI_CHANGING_LAYOUT) != 0) {
+            // If the navigation bar has been hidden or shown, we need to do another
+            // layout pass to update that window.
+            changes |= FINISH_LAYOUT_REDO_LAYOUT;
+        }
+
+        if (mShowingDream != mLastShowingDream) {
+            mLastShowingDream = mShowingDream;
+            mService.notifyShowingDreamChanged();
+        }
+
+        updateWindowSleepToken();
+
+        mService.mPolicy.setAllowLockscreenWhenOn(getDisplayId(), mAllowLockscreenWhenOn);
+        return changes;
+    }
+
+    private void updateWindowSleepToken() {
+        if (mWindowSleepTokenNeeded && !mLastWindowSleepTokenNeeded) {
+            mHandler.removeCallbacks(mReleaseSleepTokenRunnable);
+            mHandler.post(mAcquireSleepTokenRunnable);
+        } else if (!mWindowSleepTokenNeeded && mLastWindowSleepTokenNeeded) {
+            mHandler.removeCallbacks(mAcquireSleepTokenRunnable);
+            mHandler.post(mReleaseSleepTokenRunnable);
+        }
+        mLastWindowSleepTokenNeeded = mWindowSleepTokenNeeded;
+    }
+
+    /**
+     * @return Whether the top app should hide the statusbar based on the top fullscreen opaque
+     *         window.
+     */
+    private boolean topAppHidesStatusBar() {
+        if (mTopFullscreenOpaqueWindowState == null) {
+            return false;
+        }
+        final int fl = PolicyControl.getWindowFlags(null,
+                mTopFullscreenOpaqueWindowState.getAttrs());
+        if (localLOGV) {
+            Slog.d(TAG, "frame: " + mTopFullscreenOpaqueWindowState.getFrameLw());
+            Slog.d(TAG, "attr: " + mTopFullscreenOpaqueWindowState.getAttrs()
+                    + " lp.flags=0x" + Integer.toHexString(fl));
+        }
+        return (fl & LayoutParams.FLAG_FULLSCREEN) != 0
+                || (mLastSystemUiFlags & View.SYSTEM_UI_FLAG_FULLSCREEN) != 0;
+    }
+
+    /**
+     * Called when the resource overlays change.
+     */
+    public void onOverlayChangedLw() {
+        onConfigurationChanged();
+    }
+
+    /**
+     * Called when the configuration has changed, and it's safe to load new values from resources.
+     */
+    public void onConfigurationChanged() {
+        final DisplayRotation displayRotation = mDisplayContent.getDisplayRotation();
+
+        final Context uiContext = getSystemUiContext();
+        final Resources res = uiContext.getResources();
+        final int portraitRotation = displayRotation.getPortraitRotation();
+        final int upsideDownRotation = displayRotation.getUpsideDownRotation();
+        final int landscapeRotation = displayRotation.getLandscapeRotation();
+        final int seascapeRotation = displayRotation.getSeascapeRotation();
+
+        mStatusBarHeightForRotation[portraitRotation] =
+        mStatusBarHeightForRotation[upsideDownRotation] =
+                res.getDimensionPixelSize(R.dimen.status_bar_height_portrait);
+        mStatusBarHeightForRotation[landscapeRotation] =
+        mStatusBarHeightForRotation[seascapeRotation] =
+                res.getDimensionPixelSize(R.dimen.status_bar_height_landscape);
+
+        // Height of the navigation bar when presented horizontally at bottom
+        mNavigationBarHeightForRotationDefault[portraitRotation] =
+        mNavigationBarHeightForRotationDefault[upsideDownRotation] =
+                res.getDimensionPixelSize(R.dimen.navigation_bar_height);
+        mNavigationBarHeightForRotationDefault[landscapeRotation] =
+        mNavigationBarHeightForRotationDefault[seascapeRotation] =
+                res.getDimensionPixelSize(R.dimen.navigation_bar_height_landscape);
+
+        // Width of the navigation bar when presented vertically along one side
+        mNavigationBarWidthForRotationDefault[portraitRotation] =
+        mNavigationBarWidthForRotationDefault[upsideDownRotation] =
+        mNavigationBarWidthForRotationDefault[landscapeRotation] =
+        mNavigationBarWidthForRotationDefault[seascapeRotation] =
+                res.getDimensionPixelSize(R.dimen.navigation_bar_width);
+
+        if (ALTERNATE_CAR_MODE_NAV_SIZE) {
+            // Height of the navigation bar when presented horizontally at bottom
+            mNavigationBarHeightForRotationInCarMode[portraitRotation] =
+            mNavigationBarHeightForRotationInCarMode[upsideDownRotation] =
+                    res.getDimensionPixelSize(R.dimen.navigation_bar_height_car_mode);
+            mNavigationBarHeightForRotationInCarMode[landscapeRotation] =
+            mNavigationBarHeightForRotationInCarMode[seascapeRotation] =
+                    res.getDimensionPixelSize(R.dimen.navigation_bar_height_landscape_car_mode);
+
+            // Width of the navigation bar when presented vertically along one side
+            mNavigationBarWidthForRotationInCarMode[portraitRotation] =
+            mNavigationBarWidthForRotationInCarMode[upsideDownRotation] =
+            mNavigationBarWidthForRotationInCarMode[landscapeRotation] =
+            mNavigationBarWidthForRotationInCarMode[seascapeRotation] =
+                    res.getDimensionPixelSize(R.dimen.navigation_bar_width_car_mode);
+        }
+
+        // EXPERIMENT TODO(b/113952590): Remove once experiment in bug is completed
+        mExperiments.onConfigurationChanged(uiContext);
+        // EXPERIMENT END
+    }
+
+    @VisibleForTesting
+    Context getSystemUiContext() {
+        final Context uiContext = ActivityThread.currentActivityThread().getSystemUiContext();
+        return mDisplayContent.isDefaultDisplay
+                ? uiContext : uiContext.createDisplayContext(mDisplayContent.getDisplay());
+    }
+
+    private int getNavigationBarWidth(int rotation, int uiMode) {
+        if (ALTERNATE_CAR_MODE_NAV_SIZE && (uiMode & UI_MODE_TYPE_MASK) == UI_MODE_TYPE_CAR) {
+            return mNavigationBarWidthForRotationInCarMode[rotation];
+        } else {
+            return mNavigationBarWidthForRotationDefault[rotation];
+        }
+    }
+
+    /**
+     * Return the display width available after excluding any screen
+     * decorations that could never be removed in Honeycomb. That is, system bar or
+     * button bar.
+     */
+    public int getNonDecorDisplayWidth(int fullWidth, int fullHeight, int rotation, int uiMode,
+            DisplayCutout displayCutout) {
+        int width = fullWidth;
+        if (hasNavigationBar()) {
+            // For a basic navigation bar, when we are in landscape mode we place
+            // the navigation bar to the side.
+            if (navigationBarCanMove() && fullWidth > fullHeight) {
+                width -= getNavigationBarWidth(rotation, uiMode);
+            }
+        }
+        if (displayCutout != null) {
+            width -= displayCutout.getSafeInsetLeft() + displayCutout.getSafeInsetRight();
+        }
+        return width;
+    }
+
+    private int getNavigationBarHeight(int rotation, int uiMode) {
+        if (ALTERNATE_CAR_MODE_NAV_SIZE && (uiMode & UI_MODE_TYPE_MASK) == UI_MODE_TYPE_CAR) {
+            return mNavigationBarHeightForRotationInCarMode[rotation];
+        } else {
+            return mNavigationBarHeightForRotationDefault[rotation];
+        }
+    }
+
+    /**
+     * Return the display height available after excluding any screen
+     * decorations that could never be removed in Honeycomb. That is, system bar or
+     * button bar.
+     */
+    public int getNonDecorDisplayHeight(int fullWidth, int fullHeight, int rotation, int uiMode,
+            DisplayCutout displayCutout) {
+        int height = fullHeight;
+        if (hasNavigationBar()) {
+            // For a basic navigation bar, when we are in portrait mode we place
+            // the navigation bar to the bottom.
+            if (!navigationBarCanMove() || fullWidth < fullHeight) {
+                height -= getNavigationBarHeight(rotation, uiMode);
+            }
+        }
+        if (displayCutout != null) {
+            height -= displayCutout.getSafeInsetTop() + displayCutout.getSafeInsetBottom();
+        }
+        return height;
+    }
+
+    /**
+     * Return the available screen width that we should report for the
+     * configuration.  This must be no larger than
+     * {@link #getNonDecorDisplayWidth(int, int, int, int, DisplayCutout)}; it may be smaller
+     * than that to account for more transient decoration like a status bar.
+     */
+    public int getConfigDisplayWidth(int fullWidth, int fullHeight, int rotation, int uiMode,
+            DisplayCutout displayCutout) {
+        return getNonDecorDisplayWidth(fullWidth, fullHeight, rotation, uiMode, displayCutout);
+    }
+
+    /**
+     * Return the available screen height that we should report for the
+     * configuration.  This must be no larger than
+     * {@link #getNonDecorDisplayHeight(int, int, int, int, DisplayCutout)}; it may be smaller
+     * than that to account for more transient decoration like a status bar.
+     */
+    public int getConfigDisplayHeight(int fullWidth, int fullHeight, int rotation, int uiMode,
+            DisplayCutout displayCutout) {
+        // There is a separate status bar at the top of the display.  We don't count that as part
+        // of the fixed decor, since it can hide; however, for purposes of configurations,
+        // we do want to exclude it since applications can't generally use that part
+        // of the screen.
+        int statusBarHeight = mStatusBarHeightForRotation[rotation];
+        if (displayCutout != null) {
+            // If there is a cutout, it may already have accounted for some part of the status
+            // bar height.
+            statusBarHeight = Math.max(0, statusBarHeight - displayCutout.getSafeInsetTop());
+        }
+        return getNonDecorDisplayHeight(fullWidth, fullHeight, rotation, uiMode, displayCutout)
+                - statusBarHeight;
+    }
+
+    boolean isShowingDreamLw() {
+        return mShowingDream;
+    }
+
+    /**
+     * Calculates the stable insets without running a layout.
+     *
+     * @param displayRotation the current display rotation
+     * @param displayWidth the current display width
+     * @param displayHeight the current display height
+     * @param displayCutout the current display cutout
+     * @param outInsets the insets to return
+     */
+    public void getStableInsetsLw(int displayRotation, int displayWidth, int displayHeight,
+            DisplayCutout displayCutout, Rect outInsets) {
+        outInsets.setEmpty();
+
+        // Navigation bar and status bar.
+        getNonDecorInsetsLw(displayRotation, displayWidth, displayHeight, displayCutout, outInsets);
+        outInsets.top = Math.max(outInsets.top, mStatusBarHeightForRotation[displayRotation]);
+    }
+
+    /**
+     * Calculates the insets for the areas that could never be removed in Honeycomb, i.e. system
+     * bar or button bar. See {@link #getNonDecorDisplayWidth}.
+     *
+     * @param displayRotation the current display rotation
+     * @param displayWidth the current display width
+     * @param displayHeight the current display height
+     * @param displayCutout the current display cutout
+     * @param outInsets the insets to return
+     */
+    public void getNonDecorInsetsLw(int displayRotation, int displayWidth, int displayHeight,
+            DisplayCutout displayCutout, Rect outInsets) {
+        outInsets.setEmpty();
+
+        // Only navigation bar
+        if (hasNavigationBar()) {
+            final int uiMode = mService.mPolicy.getUiMode();
+            int position = navigationBarPosition(displayWidth, displayHeight, displayRotation);
+            if (position == NAV_BAR_BOTTOM) {
+                outInsets.bottom = getNavigationBarHeight(displayRotation, uiMode);
+            } else if (position == NAV_BAR_RIGHT) {
+                outInsets.right = getNavigationBarWidth(displayRotation, uiMode);
+            } else if (position == NAV_BAR_LEFT) {
+                outInsets.left = getNavigationBarWidth(displayRotation, uiMode);
+            }
+        }
+
+        if (displayCutout != null) {
+            outInsets.left += displayCutout.getSafeInsetLeft();
+            outInsets.top += displayCutout.getSafeInsetTop();
+            outInsets.right += displayCutout.getSafeInsetRight();
+            outInsets.bottom += displayCutout.getSafeInsetBottom();
+        }
+    }
+
+    @NavigationBarPosition
+    int navigationBarPosition(int displayWidth, int displayHeight, int displayRotation) {
+        if (navigationBarCanMove() && displayWidth > displayHeight) {
+            if (displayRotation == Surface.ROTATION_270) {
+                return NAV_BAR_LEFT;
+            } else if (displayRotation == Surface.ROTATION_90) {
+                return NAV_BAR_RIGHT;
+            }
+        }
+        return NAV_BAR_BOTTOM;
+    }
+
+    /**
+     * @return The side of the screen where navigation bar is positioned.
+     * @see WindowManagerPolicyConstants#NAV_BAR_LEFT
+     * @see WindowManagerPolicyConstants#NAV_BAR_RIGHT
+     * @see WindowManagerPolicyConstants#NAV_BAR_BOTTOM
+     */
+    @NavigationBarPosition
+    public int getNavBarPosition() {
+        return mNavigationBarPosition;
+    }
+
+    /**
+     * A new window has been focused.
+     */
+    public int focusChangedLw(WindowState lastFocus, WindowState newFocus) {
+        mFocusedWindow = newFocus;
+        mLastFocusedWindow = lastFocus;
+        if ((updateSystemUiVisibilityLw() & SYSTEM_UI_CHANGING_LAYOUT) != 0) {
+            // If the navigation bar has been hidden or shown, we need to do another
+            // layout pass to update that window.
+            return FINISH_LAYOUT_REDO_LAYOUT;
+        }
+        return 0;
+    }
+
+    /**
+     * Return true if it is okay to perform animations for an app transition
+     * that is about to occur. You may return false for this if, for example,
+     * the dream window is currently displayed so the switch should happen
+     * immediately.
+     */
+    public boolean allowAppAnimationsLw() {
+        return !mShowingDream;
+    }
+
+    private void updateDreamingSleepToken(boolean acquire) {
+        if (acquire) {
+            final int displayId = getDisplayId();
+            if (mDreamingSleepToken == null) {
+                mDreamingSleepToken = mService.mAtmInternal.acquireSleepToken(
+                        "DreamOnDisplay" + displayId, displayId);
+            }
+        } else {
+            if (mDreamingSleepToken != null) {
+                mDreamingSleepToken.release();
+                mDreamingSleepToken = null;
+            }
+        }
+    }
+
+    private void requestTransientBars(WindowState swipeTarget) {
+        synchronized (mLock) {
+            if (!mService.mPolicy.isUserSetupComplete()) {
+                // Swipe-up for navigation bar is disabled during setup
+                return;
+            }
+            boolean sb = mStatusBarController.checkShowTransientBarLw();
+            boolean nb = mNavigationBarController.checkShowTransientBarLw()
+                    && !isNavBarEmpty(mLastSystemUiFlags);
+            if (sb || nb) {
+                // Don't show status bar when swiping on already visible navigation bar
+                if (!nb && swipeTarget == mNavigationBar) {
+                    if (DEBUG) Slog.d(TAG, "Not showing transient bar, wrong swipe target");
+                    return;
+                }
+                if (sb) mStatusBarController.showTransient();
+                if (nb) mNavigationBarController.showTransient();
+                mImmersiveModeConfirmation.confirmCurrentPrompt();
+                updateSystemUiVisibilityLw();
+            }
+        }
+    }
+
+    private void disposeInputConsumer(InputConsumer inputConsumer) {
+        if (inputConsumer != null) {
+            inputConsumer.dismiss();
+        }
+    }
+
+    private boolean isStatusBarKeyguard() {
+        return mStatusBar != null
+                && (mStatusBar.getAttrs().privateFlags & PRIVATE_FLAG_KEYGUARD) != 0;
+    }
+
+    private boolean isKeyguardOccluded() {
+        // TODO (b/113840485): Handle per display keyguard.
+        return mService.mPolicy.isKeyguardOccluded();
+    }
+
+    void resetSystemUiVisibilityLw() {
+        mLastSystemUiFlags = 0;
+        updateSystemUiVisibilityLw();
+    }
+
+    private int updateSystemUiVisibilityLw() {
+        // If there is no window focused, there will be nobody to handle the events
+        // anyway, so just hang on in whatever state we're in until things settle down.
+        WindowState winCandidate = mFocusedWindow != null ? mFocusedWindow
+                : mTopFullscreenOpaqueWindowState;
+        if (winCandidate == null) {
+            return 0;
+        }
+
+        // The immersive mode confirmation should never affect the system bar visibility, otherwise
+        // it will unhide the navigation bar and hide itself.
+        if (winCandidate.getAttrs().token == mImmersiveModeConfirmation.getWindowToken()) {
+
+            // The immersive mode confirmation took the focus from mLastFocusedWindow which was
+            // controlling the system ui visibility. So if mLastFocusedWindow can still receive
+            // keys, we let it keep controlling the visibility.
+            final boolean lastFocusCanReceiveKeys =
+                    (mLastFocusedWindow != null && mLastFocusedWindow.canReceiveKeys());
+            winCandidate = isStatusBarKeyguard() ? mStatusBar
+                    : lastFocusCanReceiveKeys ? mLastFocusedWindow
+                            : mTopFullscreenOpaqueWindowState;
+            if (winCandidate == null) {
+                return 0;
+            }
+        }
+        final WindowState win = winCandidate;
+        if ((win.getAttrs().privateFlags & PRIVATE_FLAG_KEYGUARD) != 0 && isKeyguardOccluded()) {
+            // We are updating at a point where the keyguard has gotten
+            // focus, but we were last in a state where the top window is
+            // hiding it.  This is probably because the keyguard as been
+            // shown while the top window was displayed, so we want to ignore
+            // it here because this is just a very transient change and it
+            // will quickly lose focus once it correctly gets hidden.
+            return 0;
+        }
+
+        int tmpVisibility = PolicyControl.getSystemUiVisibility(win, null)
+                & ~mResettingSystemUiFlags
+                & ~mForceClearedSystemUiFlags;
+        if (mForcingShowNavBar && win.getSurfaceLayer() < mForcingShowNavBarLayer) {
+            tmpVisibility
+                    &= ~PolicyControl.adjustClearableFlags(win, View.SYSTEM_UI_CLEARABLE_FLAGS);
+        }
+
+        final int fullscreenVisibility = updateLightStatusBarLw(0 /* vis */,
+                mTopFullscreenOpaqueWindowState, mTopFullscreenOpaqueOrDimmingWindowState);
+        final int dockedVisibility = updateLightStatusBarLw(0 /* vis */,
+                mTopDockedOpaqueWindowState, mTopDockedOpaqueOrDimmingWindowState);
+        mService.getStackBounds(
+                WINDOWING_MODE_UNDEFINED, ACTIVITY_TYPE_HOME, mNonDockedStackBounds);
+        mService.getStackBounds(
+                WINDOWING_MODE_SPLIT_SCREEN_PRIMARY, ACTIVITY_TYPE_STANDARD, mDockedStackBounds);
+        final int visibility = updateSystemBarsLw(win, mLastSystemUiFlags, tmpVisibility);
+        final int diff = visibility ^ mLastSystemUiFlags;
+        final int fullscreenDiff = fullscreenVisibility ^ mLastFullscreenStackSysUiFlags;
+        final int dockedDiff = dockedVisibility ^ mLastDockedStackSysUiFlags;
+        final boolean needsMenu = win.getNeedsMenuLw(mTopFullscreenOpaqueWindowState);
+        if (diff == 0 && fullscreenDiff == 0 && dockedDiff == 0 && mLastFocusNeedsMenu == needsMenu
+                && mFocusedApp == win.getAppToken()
+                && mLastNonDockedStackBounds.equals(mNonDockedStackBounds)
+                && mLastDockedStackBounds.equals(mDockedStackBounds)) {
+            return 0;
+        }
+        mLastSystemUiFlags = visibility;
+        mLastFullscreenStackSysUiFlags = fullscreenVisibility;
+        mLastDockedStackSysUiFlags = dockedVisibility;
+        mLastFocusNeedsMenu = needsMenu;
+        mFocusedApp = win.getAppToken();
+        final Rect fullscreenStackBounds = new Rect(mNonDockedStackBounds);
+        final Rect dockedStackBounds = new Rect(mDockedStackBounds);
+        mHandler.post(() -> {
+            StatusBarManagerInternal statusBar = getStatusBarManagerInternal();
+            if (statusBar != null) {
+                final int displayId = getDisplayId();
+                statusBar.setSystemUiVisibility(displayId, visibility, fullscreenVisibility,
+                        dockedVisibility, 0xffffffff, fullscreenStackBounds,
+                        dockedStackBounds, win.toString());
+                statusBar.topAppWindowChanged(displayId, needsMenu);
+            }
+        });
+        return diff;
+    }
+
+    private int updateLightStatusBarLw(int vis, WindowState opaque, WindowState opaqueOrDimming) {
+        final boolean onKeyguard = isStatusBarKeyguard() && !isKeyguardOccluded();
+        final WindowState statusColorWin = onKeyguard ? mStatusBar : opaqueOrDimming;
+        if (statusColorWin != null && (statusColorWin == opaque || onKeyguard)) {
+            // If the top fullscreen-or-dimming window is also the top fullscreen, respect
+            // its light flag.
+            vis &= ~View.SYSTEM_UI_FLAG_LIGHT_STATUS_BAR;
+            vis |= PolicyControl.getSystemUiVisibility(statusColorWin, null)
+                    & View.SYSTEM_UI_FLAG_LIGHT_STATUS_BAR;
+        } else if (statusColorWin != null && statusColorWin.isDimming()) {
+            // Otherwise if it's dimming, clear the light flag.
+            vis &= ~View.SYSTEM_UI_FLAG_LIGHT_STATUS_BAR;
+        }
+        return vis;
+    }
+
+    @VisibleForTesting
+    @Nullable
+    static WindowState chooseNavigationColorWindowLw(WindowState opaque,
+            WindowState opaqueOrDimming, WindowState imeWindow,
+            @NavigationBarPosition int navBarPosition) {
+        // If the IME window is visible and FLAG_DRAWS_SYSTEM_BAR_BACKGROUNDS is set, then IME
+        // window can be navigation color window.
+        final boolean imeWindowCanNavColorWindow = imeWindow != null
+                && imeWindow.isVisibleLw()
+                && navBarPosition == NAV_BAR_BOTTOM
+                && (PolicyControl.getWindowFlags(imeWindow, null)
+                & WindowManager.LayoutParams.FLAG_DRAWS_SYSTEM_BAR_BACKGROUNDS) != 0;
+
+        if (opaque != null && opaqueOrDimming == opaque) {
+            // If the top fullscreen-or-dimming window is also the top fullscreen, respect it
+            // unless IME window is also eligible, since currently the IME window is always show
+            // above the opaque fullscreen app window, regardless of the IME target window.
+            // TODO(b/31559891): Maybe we need to revisit this condition once b/31559891 is fixed.
+            return imeWindowCanNavColorWindow ? imeWindow : opaque;
+        }
+
+        if (opaqueOrDimming == null || !opaqueOrDimming.isDimming()) {
+            // No dimming window is involved. Determine the result only with the IME window.
+            return imeWindowCanNavColorWindow ? imeWindow : null;
+        }
+
+        if (!imeWindowCanNavColorWindow) {
+            // No IME window is involved. Determine the result only with opaqueOrDimming.
+            return opaqueOrDimming;
+        }
+
+        // The IME window and the dimming window are competing.  Check if the dimming window can be
+        // IME target or not.
+        if (LayoutParams.mayUseInputMethod(PolicyControl.getWindowFlags(opaqueOrDimming, null))) {
+            // The IME window is above the dimming window.
+            return imeWindow;
+        } else {
+            // The dimming window is above the IME window.
+            return opaqueOrDimming;
+        }
+    }
+
+    @VisibleForTesting
+    static int updateLightNavigationBarLw(int vis, WindowState opaque, WindowState opaqueOrDimming,
+            WindowState imeWindow, WindowState navColorWin) {
+
+        if (navColorWin != null) {
+            if (navColorWin == imeWindow || navColorWin == opaque) {
+                // Respect the light flag.
+                vis &= ~View.SYSTEM_UI_FLAG_LIGHT_NAVIGATION_BAR;
+                vis |= PolicyControl.getSystemUiVisibility(navColorWin, null)
+                        & View.SYSTEM_UI_FLAG_LIGHT_NAVIGATION_BAR;
+            } else if (navColorWin == opaqueOrDimming && navColorWin.isDimming()) {
+                // Clear the light flag for dimming window.
+                vis &= ~View.SYSTEM_UI_FLAG_LIGHT_NAVIGATION_BAR;
+            }
+        }
+        return vis;
+    }
+
+    private int updateSystemBarsLw(WindowState win, int oldVis, int vis) {
+        final boolean dockedStackVisible =
+                mDisplayContent.isStackVisible(WINDOWING_MODE_SPLIT_SCREEN_PRIMARY);
+        final boolean freeformStackVisible =
+                mDisplayContent.isStackVisible(WINDOWING_MODE_FREEFORM);
+        final boolean resizing = mDisplayContent.getDockedDividerController().isResizing();
+
+        // We need to force system bars when the docked stack is visible, when the freeform stack
+        // is visible but also when we are resizing for the transitions when docked stack
+        // visibility changes.
+        mForceShowSystemBars = dockedStackVisible || freeformStackVisible || resizing;
+        final boolean forceOpaqueStatusBar = mForceShowSystemBars && !mForceStatusBarFromKeyguard;
+
+        // apply translucent bar vis flags
+        WindowState fullscreenTransWin = isStatusBarKeyguard() && !isKeyguardOccluded()
+                ? mStatusBar
+                : mTopFullscreenOpaqueWindowState;
+        vis = mStatusBarController.applyTranslucentFlagLw(fullscreenTransWin, vis, oldVis);
+        vis = mNavigationBarController.applyTranslucentFlagLw(fullscreenTransWin, vis, oldVis);
+        final int dockedVis = mStatusBarController.applyTranslucentFlagLw(
+                mTopDockedOpaqueWindowState, 0, 0);
+
+        final boolean fullscreenDrawsStatusBarBackground =
+                drawsStatusBarBackground(vis, mTopFullscreenOpaqueWindowState);
+        final boolean dockedDrawsStatusBarBackground =
+                drawsStatusBarBackground(dockedVis, mTopDockedOpaqueWindowState);
+
+        // prevent status bar interaction from clearing certain flags
+        int type = win.getAttrs().type;
+        boolean statusBarHasFocus = type == TYPE_STATUS_BAR;
+        if (statusBarHasFocus && !isStatusBarKeyguard()) {
+            int flags = View.SYSTEM_UI_FLAG_FULLSCREEN
+                    | View.SYSTEM_UI_FLAG_HIDE_NAVIGATION
+                    | View.SYSTEM_UI_FLAG_IMMERSIVE
+                    | View.SYSTEM_UI_FLAG_IMMERSIVE_STICKY
+                    | View.SYSTEM_UI_FLAG_LIGHT_STATUS_BAR;
+            if (isKeyguardOccluded()) {
+                flags |= View.STATUS_BAR_TRANSLUCENT | View.NAVIGATION_BAR_TRANSLUCENT;
+            }
+            vis = (vis & ~flags) | (oldVis & flags);
+        }
+
+        if (fullscreenDrawsStatusBarBackground && dockedDrawsStatusBarBackground) {
+            vis |= View.STATUS_BAR_TRANSPARENT;
+            vis &= ~View.STATUS_BAR_TRANSLUCENT;
+        } else if ((!areTranslucentBarsAllowed() && fullscreenTransWin != mStatusBar)
+                || forceOpaqueStatusBar) {
+            vis &= ~(View.STATUS_BAR_TRANSLUCENT | View.STATUS_BAR_TRANSPARENT);
+        }
+
+        vis = configureNavBarOpacity(vis, dockedStackVisible, freeformStackVisible, resizing);
+
+        // update status bar
+        boolean immersiveSticky =
+                (vis & View.SYSTEM_UI_FLAG_IMMERSIVE_STICKY) != 0;
+        final boolean hideStatusBarWM =
+                mTopFullscreenOpaqueWindowState != null
+                        && (PolicyControl.getWindowFlags(mTopFullscreenOpaqueWindowState, null)
+                        & WindowManager.LayoutParams.FLAG_FULLSCREEN) != 0;
+        final boolean hideStatusBarSysui =
+                (vis & View.SYSTEM_UI_FLAG_FULLSCREEN) != 0;
+        final boolean hideNavBarSysui =
+                (vis & View.SYSTEM_UI_FLAG_HIDE_NAVIGATION) != 0;
+
+        final boolean transientStatusBarAllowed = mStatusBar != null
+                && (statusBarHasFocus || (!mForceShowSystemBars
+                && (hideStatusBarWM || (hideStatusBarSysui && immersiveSticky))));
+
+        final boolean transientNavBarAllowed = mNavigationBar != null
+                && !mForceShowSystemBars && hideNavBarSysui && immersiveSticky;
+
+        final long now = SystemClock.uptimeMillis();
+        final boolean pendingPanic = mPendingPanicGestureUptime != 0
+                && now - mPendingPanicGestureUptime <= PANIC_GESTURE_EXPIRATION;
+        final DisplayPolicy defaultDisplayPolicy =
+                mService.getDefaultDisplayContentLocked().getDisplayPolicy();
+        if (pendingPanic && hideNavBarSysui && !isStatusBarKeyguard()
+                // TODO (b/111955725): Show keyguard presentation on all external displays
+                && defaultDisplayPolicy.isKeyguardDrawComplete()) {
+            // The user performed the panic gesture recently, we're about to hide the bars,
+            // we're no longer on the Keyguard and the screen is ready. We can now request the bars.
+            mPendingPanicGestureUptime = 0;
+            mStatusBarController.showTransient();
+            if (!isNavBarEmpty(vis)) {
+                mNavigationBarController.showTransient();
+            }
+        }
+
+        final boolean denyTransientStatus = mStatusBarController.isTransientShowRequested()
+                && !transientStatusBarAllowed && hideStatusBarSysui;
+        final boolean denyTransientNav = mNavigationBarController.isTransientShowRequested()
+                && !transientNavBarAllowed;
+        if (denyTransientStatus || denyTransientNav || mForceShowSystemBars) {
+            // clear the clearable flags instead
+            clearClearableFlagsLw();
+            vis &= ~View.SYSTEM_UI_CLEARABLE_FLAGS;
+        }
+
+        final boolean immersive = (vis & View.SYSTEM_UI_FLAG_IMMERSIVE) != 0;
+        immersiveSticky = (vis & View.SYSTEM_UI_FLAG_IMMERSIVE_STICKY) != 0;
+        final boolean navAllowedHidden = immersive || immersiveSticky;
+
+        if (hideNavBarSysui && !navAllowedHidden
+                && mService.mPolicy.getWindowLayerLw(win)
+                        > mService.mPolicy.getWindowLayerFromTypeLw(TYPE_INPUT_CONSUMER)) {
+            // We can't hide the navbar from this window otherwise the input consumer would not get
+            // the input events.
+            vis = (vis & ~View.SYSTEM_UI_FLAG_HIDE_NAVIGATION);
+        }
+
+        vis = mStatusBarController.updateVisibilityLw(transientStatusBarAllowed, oldVis, vis);
+
+        // update navigation bar
+        boolean oldImmersiveMode = isImmersiveMode(oldVis);
+        boolean newImmersiveMode = isImmersiveMode(vis);
+        if (oldImmersiveMode != newImmersiveMode) {
+            final String pkg = win.getOwningPackage();
+            mImmersiveModeConfirmation.immersiveModeChangedLw(pkg, newImmersiveMode,
+                    mService.mPolicy.isUserSetupComplete(),
+                    isNavBarEmpty(win.getSystemUiVisibility()));
+        }
+
+        vis = mNavigationBarController.updateVisibilityLw(transientNavBarAllowed, oldVis, vis);
+
+        final WindowState navColorWin = chooseNavigationColorWindowLw(
+                mTopFullscreenOpaqueWindowState, mTopFullscreenOpaqueOrDimmingWindowState,
+                mDisplayContent.mInputMethodWindow, mNavigationBarPosition);
+        vis = updateLightNavigationBarLw(vis, mTopFullscreenOpaqueWindowState,
+                mTopFullscreenOpaqueOrDimmingWindowState,
+                mDisplayContent.mInputMethodWindow, navColorWin);
+
+        return vis;
+    }
+
+    private boolean drawsStatusBarBackground(int vis, WindowState win) {
+        if (!mStatusBarController.isTransparentAllowed(win)) {
+            return false;
+        }
+        if (win == null) {
+            return true;
+        }
+
+        final boolean drawsSystemBars =
+                (win.getAttrs().flags & FLAG_DRAWS_SYSTEM_BAR_BACKGROUNDS) != 0;
+        final boolean forceDrawsSystemBars =
+                (win.getAttrs().privateFlags & PRIVATE_FLAG_FORCE_DRAW_STATUS_BAR_BACKGROUND) != 0;
+
+        return forceDrawsSystemBars || drawsSystemBars && (vis & View.STATUS_BAR_TRANSLUCENT) == 0;
+    }
+
+    /**
+     * @return the current visibility flags with the nav-bar opacity related flags toggled based
+     *         on the nav bar opacity rules chosen by {@link #mNavBarOpacityMode}.
+     */
+    private int configureNavBarOpacity(int visibility, boolean dockedStackVisible,
+            boolean freeformStackVisible, boolean isDockedDividerResizing) {
+        if (mNavBarOpacityMode == NAV_BAR_OPAQUE_WHEN_FREEFORM_OR_DOCKED) {
+            if (dockedStackVisible || freeformStackVisible || isDockedDividerResizing) {
+                visibility = setNavBarOpaqueFlag(visibility);
+            }
+        } else if (mNavBarOpacityMode == NAV_BAR_TRANSLUCENT_WHEN_FREEFORM_OPAQUE_OTHERWISE) {
+            if (isDockedDividerResizing) {
+                visibility = setNavBarOpaqueFlag(visibility);
+            } else if (freeformStackVisible) {
+                visibility = setNavBarTranslucentFlag(visibility);
+            } else {
+                visibility = setNavBarOpaqueFlag(visibility);
+            }
+        }
+
+        if (!areTranslucentBarsAllowed()) {
+            visibility &= ~View.NAVIGATION_BAR_TRANSLUCENT;
+        }
+        return visibility;
+    }
+
+    private int setNavBarOpaqueFlag(int visibility) {
+        return visibility & ~(View.NAVIGATION_BAR_TRANSLUCENT | View.NAVIGATION_BAR_TRANSPARENT);
+    }
+
+    private int setNavBarTranslucentFlag(int visibility) {
+        visibility &= ~View.NAVIGATION_BAR_TRANSPARENT;
+        return visibility | View.NAVIGATION_BAR_TRANSLUCENT;
+    }
+
+    private void clearClearableFlagsLw() {
+        int newVal = mResettingSystemUiFlags | View.SYSTEM_UI_CLEARABLE_FLAGS;
+        if (newVal != mResettingSystemUiFlags) {
+            mResettingSystemUiFlags = newVal;
+            mDisplayContent.reevaluateStatusBarVisibility();
+        }
+    }
+
+    private boolean isImmersiveMode(int vis) {
+        final int flags = View.SYSTEM_UI_FLAG_IMMERSIVE | View.SYSTEM_UI_FLAG_IMMERSIVE_STICKY;
+        return mNavigationBar != null
+                && (vis & View.SYSTEM_UI_FLAG_HIDE_NAVIGATION) != 0
+                && (vis & flags) != 0
+                && canHideNavigationBar();
+    }
+
+    /**
+     * @return whether the navigation bar can be hidden, e.g. the device has a navigation bar
+     */
+    private boolean canHideNavigationBar() {
+        return hasNavigationBar();
+    }
+
+    private static boolean isNavBarEmpty(int systemUiFlags) {
+        final int disableNavigationBar = (View.STATUS_BAR_DISABLE_HOME
+                | View.STATUS_BAR_DISABLE_BACK
+                | View.STATUS_BAR_DISABLE_RECENT);
+
+        return (systemUiFlags & disableNavigationBar) == disableNavigationBar;
+    }
+
+    /**
+     * @return whether the navigation or status bar can be made translucent
+     *
+     * This should return true unless touch exploration is not enabled or
+     * R.boolean.config_enableTranslucentDecor is false.
+     */
+    private boolean areTranslucentBarsAllowed() {
+        return mTranslucentDecorEnabled;
+    }
+
+    boolean shouldRotateSeamlessly(DisplayRotation displayRotation, int oldRotation,
+            int newRotation) {
+        // For the upside down rotation we don't rotate seamlessly as the navigation
+        // bar moves position.
+        // Note most apps (using orientation:sensor or user as opposed to fullSensor)
+        // will not enter the reverse portrait orientation, so actually the
+        // orientation won't change at all.
+        if (oldRotation == displayRotation.getUpsideDownRotation()
+                || newRotation == displayRotation.getUpsideDownRotation()) {
+            return false;
+        }
+        // If the navigation bar can't change sides, then it will
+        // jump when we change orientations and we don't rotate
+        // seamlessly.
+        if (!navigationBarCanMove()) {
+            return false;
+        }
+
+        final WindowState w = mTopFullscreenOpaqueWindowState;
+        if (w != mFocusedWindow) {
+            return false;
+        }
+
+        // We only enable seamless rotation if the top window has requested
+        // it and is in the fullscreen opaque state. Seamless rotation
+        // requires freezing various Surface states and won't work well
+        // with animations, so we disable it in the animation case for now.
+        if (w != null && !w.isAnimatingLw()
+                && w.getAttrs().rotationAnimation == ROTATION_ANIMATION_SEAMLESS) {
+            return true;
+        }
+        return false;
+    }
+
+    private final Runnable mHiddenNavPanic = new Runnable() {
+        @Override
+        public void run() {
+            synchronized (mLock) {
+                if (!mService.mPolicy.isUserSetupComplete()) {
+                    // Swipe-up for navigation bar is disabled during setup
+                    return;
+                }
+                mPendingPanicGestureUptime = SystemClock.uptimeMillis();
+                if (!isNavBarEmpty(mLastSystemUiFlags)) {
+                    mNavigationBarController.showTransient();
+                }
+            }
+        }
+    };
+
+    void onPowerKeyDown(boolean isScreenOn) {
+        // Detect user pressing the power button in panic when an application has
+        // taken over the whole screen.
+        boolean panic = mImmersiveModeConfirmation.onPowerKeyDown(isScreenOn,
+                SystemClock.elapsedRealtime(), isImmersiveMode(mLastSystemUiFlags),
+                isNavBarEmpty(mLastSystemUiFlags));
+        if (panic) {
+            mHandler.post(mHiddenNavPanic);
+        }
+    }
+
+    void onVrStateChangedLw(boolean enabled) {
+        mImmersiveModeConfirmation.onVrStateChangedLw(enabled);
+    }
+
+    /**
+     * Called when the state of lock task mode changes. This should be used to disable immersive
+     * mode confirmation.
+     *
+     * @param lockTaskState the new lock task mode state. One of
+     *                      {@link ActivityManager#LOCK_TASK_MODE_NONE},
+     *                      {@link ActivityManager#LOCK_TASK_MODE_LOCKED},
+     *                      {@link ActivityManager#LOCK_TASK_MODE_PINNED}.
+     */
+    public void onLockTaskStateChangedLw(int lockTaskState) {
+        mImmersiveModeConfirmation.onLockTaskModeChangedLw(lockTaskState);
+    }
+
+    /**
+     * Request a screenshot be taken.
+     *
+     * @param screenshotType The type of screenshot, for example either
+     *                       {@link WindowManager#TAKE_SCREENSHOT_FULLSCREEN} or
+     *                       {@link WindowManager#TAKE_SCREENSHOT_SELECTED_REGION}
+     */
+    public void takeScreenshot(int screenshotType) {
+        if (mScreenshotHelper != null) {
+            mScreenshotHelper.takeScreenshot(screenshotType,
+                    mStatusBar != null && mStatusBar.isVisibleLw(),
+                    mNavigationBar != null && mNavigationBar.isVisibleLw(), mHandler);
+        }
+    }
+
     void dump(String prefix, PrintWriter pw) {
-        pw.println(prefix + "DisplayPolicy");
-        pw.print(prefix + "  mCarDockEnablesAccelerometer=" + mCarDockEnablesAccelerometer);
-        pw.println(" mDeskDockEnablesAccelerometer=" + mDeskDockEnablesAccelerometer);
-        pw.print(prefix + "  mDockMode=" + Intent.dockStateToString(mDockMode));
-        pw.println(" mLidState=" + WindowManagerFuncs.lidStateToString(mLidState));
-        pw.print(prefix + "  mAwake=" + mAwake);
-        pw.print(" mScreenOnEarly=" + mScreenOnEarly);
-        pw.println(" mScreenOnFully=" + mScreenOnFully);
-        pw.print(prefix + "  mKeyguardDrawComplete=" + mKeyguardDrawComplete);
-        pw.println(" mWindowManagerDrawComplete=" + mWindowManagerDrawComplete);
-        pw.println(prefix + "  mHdmiPlugged=" + mHdmiPlugged);
+        pw.print(prefix); pw.print("DisplayPolicy");
+        prefix += "  ";
+        pw.print(prefix);
+        pw.print("mCarDockEnablesAccelerometer="); pw.print(mCarDockEnablesAccelerometer);
+        pw.print(" mDeskDockEnablesAccelerometer=");
+        pw.println(mDeskDockEnablesAccelerometer);
+        pw.print(prefix); pw.print("mDockMode="); pw.print(Intent.dockStateToString(mDockMode));
+        pw.print(" mLidState="); pw.println(WindowManagerFuncs.lidStateToString(mLidState));
+        pw.print(prefix); pw.print("mAwake="); pw.print(mAwake);
+        pw.print(" mScreenOnEarly="); pw.print(mScreenOnEarly);
+        pw.print(" mScreenOnFully="); pw.println(mScreenOnFully);
+        pw.print(prefix); pw.print("mKeyguardDrawComplete="); pw.print(mKeyguardDrawComplete);
+        pw.print(" mWindowManagerDrawComplete="); pw.println(mWindowManagerDrawComplete);
+        pw.print(prefix); pw.print("mHdmiPlugged="); pw.println(mHdmiPlugged);
+        if (mLastSystemUiFlags != 0 || mResettingSystemUiFlags != 0
+                || mForceClearedSystemUiFlags != 0) {
+            pw.print(prefix); pw.print("mLastSystemUiFlags=0x");
+            pw.print(Integer.toHexString(mLastSystemUiFlags));
+            pw.print(" mResettingSystemUiFlags=0x");
+            pw.print(Integer.toHexString(mResettingSystemUiFlags));
+            pw.print(" mForceClearedSystemUiFlags=0x");
+            pw.println(Integer.toHexString(mForceClearedSystemUiFlags));
+        }
+        if (mLastFocusNeedsMenu) {
+            pw.print(prefix); pw.print("mLastFocusNeedsMenu="); pw.println(mLastFocusNeedsMenu);
+        }
+        pw.print(prefix); pw.print("mShowingDream="); pw.print(mShowingDream);
+        pw.print(" mDreamingLockscreen="); pw.print(mDreamingLockscreen);
+        pw.print(" mDreamingSleepToken="); pw.println(mDreamingSleepToken);
+        if (mStatusBar != null) {
+            pw.print(prefix); pw.print("mStatusBar="); pw.print(mStatusBar);
+                    pw.print(" isStatusBarKeyguard="); pw.println(isStatusBarKeyguard());
+        }
+        if (mNavigationBar != null) {
+            pw.print(prefix); pw.print("mNavigationBar="); pw.println(mNavigationBar);
+        }
+        if (mFocusedWindow != null) {
+            pw.print(prefix); pw.print("mFocusedWindow="); pw.println(mFocusedWindow);
+        }
+        if (mFocusedApp != null) {
+            pw.print(prefix); pw.print("mFocusedApp="); pw.println(mFocusedApp);
+        }
+        if (mTopFullscreenOpaqueWindowState != null) {
+            pw.print(prefix); pw.print("mTopFullscreenOpaqueWindowState=");
+            pw.println(mTopFullscreenOpaqueWindowState);
+        }
+        if (mTopFullscreenOpaqueOrDimmingWindowState != null) {
+            pw.print(prefix); pw.print("mTopFullscreenOpaqueOrDimmingWindowState=");
+            pw.println(mTopFullscreenOpaqueOrDimmingWindowState);
+        }
+        if (mForcingShowNavBar) {
+            pw.print(prefix); pw.print("mForcingShowNavBar="); pw.println(mForcingShowNavBar);
+            pw.print(prefix); pw.print("mForcingShowNavBarLayer=");
+            pw.println(mForcingShowNavBarLayer);
+        }
+        pw.print(prefix); pw.print("mTopIsFullscreen="); pw.print(mTopIsFullscreen);
+        pw.print(prefix); pw.print("mForceStatusBar="); pw.print(mForceStatusBar);
+        pw.print(" mForceStatusBarFromKeyguard="); pw.println(mForceStatusBarFromKeyguard);
+        pw.print(prefix); pw.print("mAllowLockscreenWhenOn="); pw.println(mAllowLockscreenWhenOn);
+        mStatusBarController.dump(pw, prefix);
+        mNavigationBarController.dump(pw, prefix);
+
+        pw.print(prefix); pw.println("Looper state:");
+        mHandler.getLooper().dump(new PrintWriterPrinter(pw), prefix + "  ");
     }
 }
diff --git a/services/core/java/com/android/server/wm/DisplayRotation.java b/services/core/java/com/android/server/wm/DisplayRotation.java
index 6ab7090..f1d1e49 100644
--- a/services/core/java/com/android/server/wm/DisplayRotation.java
+++ b/services/core/java/com/android/server/wm/DisplayRotation.java
@@ -844,9 +844,9 @@
         pw.print(prefix + "  mPortraitRotation=" + Surface.rotationToString(mPortraitRotation));
         pw.println(" mUpsideDownRotation=" + Surface.rotationToString(mUpsideDownRotation));
 
-        pw.print(prefix + "  mSupportAutoRotation=" + mSupportAutoRotation);
+        pw.println(prefix + "  mSupportAutoRotation=" + mSupportAutoRotation);
         if (mOrientationListener != null) {
-            pw.print(" mOrientationSensorEnabled=" + mOrientationListener.mEnabled);
+            mOrientationListener.dump(pw, prefix + "  ");
         }
         pw.println();
 
diff --git a/services/core/java/com/android/server/wm/DockedStackDividerController.java b/services/core/java/com/android/server/wm/DockedStackDividerController.java
index c377072..7ea88bb 100644
--- a/services/core/java/com/android/server/wm/DockedStackDividerController.java
+++ b/services/core/java/com/android/server/wm/DockedStackDividerController.java
@@ -28,6 +28,8 @@
 import static android.view.WindowManager.DOCKED_RIGHT;
 import static android.view.WindowManager.DOCKED_TOP;
 import static android.view.WindowManager.TRANSIT_NONE;
+import static android.view.WindowManagerPolicyConstants.NAV_BAR_LEFT;
+import static android.view.WindowManagerPolicyConstants.NAV_BAR_RIGHT;
 
 import static com.android.server.wm.AppTransition.DEFAULT_APP_TRANSITION_DURATION;
 import static com.android.server.wm.AppTransition.TOUCH_RESPONSE_INTERPOLATOR;
@@ -52,6 +54,7 @@
 import android.view.animation.Interpolator;
 import android.view.animation.PathInterpolator;
 
+import com.android.internal.annotations.VisibleForTesting;
 import com.android.internal.policy.DividerSnapAlgorithm;
 import com.android.internal.policy.DockedDividerUtils;
 import com.android.server.LocalServices;
@@ -184,8 +187,8 @@
                     .calculateNonDismissingSnapTarget(position).position;
             DockedDividerUtils.calculateBoundsForPosition(snappedPosition, dockSide, mTmpRect,
                     mTmpRect2.width(), mTmpRect2.height(), getContentWidth());
-            mService.mPolicy.getStableInsetsLw(rotation, mTmpRect2.width(), mTmpRect2.height(),
-                    displayCutout, mTmpRect3);
+            mDisplayContent.getDisplayPolicy().getStableInsetsLw(rotation, mTmpRect2.width(),
+                    mTmpRect2.height(), displayCutout, mTmpRect3);
             mService.intersectDisplayInsetBounds(mTmpRect2, mTmpRect3, mTmpRect);
             minWidth = Math.min(mTmpRect.width(), minWidth);
         }
@@ -231,8 +234,9 @@
         final DisplayCutout displayCutout = mDisplayContent.getDisplayInfo().displayCutout;
         final int displayWidth = parentConfig.windowConfiguration.getBounds().width();
         final int displayHeight = parentConfig.windowConfiguration.getBounds().height();
-        mService.mPolicy.getStableInsetsLw(parentConfig.windowConfiguration.getRotation(),
-                displayWidth, displayHeight, displayCutout, mTmpRect);
+        mDisplayContent.getDisplayPolicy().getStableInsetsLw(
+                parentConfig.windowConfiguration.getRotation(), displayWidth, displayHeight,
+                displayCutout, mTmpRect);
         int dividerSize = mDividerWindowWidth - 2 * mDividerInsets;
         // The offset in the left (landscape)/top (portrait) is calculated with the minimized
         // offset value with the divider size and any system insets in that direction.
@@ -240,7 +244,7 @@
             outBounds.set(0, mTaskHeightInMinimizedMode + dividerSize + mTmpRect.top,
                     displayWidth, displayHeight);
         } else {
-            // In landscape also inset the left/right side with the statusbar height to match the
+            // In landscape also inset the left/right side with the status bar height to match the
             // minimized size height in portrait mode.
             final int primaryTaskWidth = mTaskHeightInMinimizedMode + dividerSize + mTmpRect.top;
             int left = mTmpRect.left;
@@ -278,16 +282,16 @@
                     : mDisplayContent.mBaseDisplayHeight;
             final DisplayCutout displayCutout =
                     mDisplayContent.calculateDisplayCutoutForRotation(rotation).getDisplayCutout();
-            mService.mPolicy.getStableInsetsLw(rotation, dw, dh, displayCutout, mTmpRect);
+            final DisplayPolicy displayPolicy =  mDisplayContent.getDisplayPolicy();
+            displayPolicy.getStableInsetsLw(rotation, dw, dh, displayCutout, mTmpRect);
             config.unset();
             config.orientation = (dw <= dh) ? ORIENTATION_PORTRAIT : ORIENTATION_LANDSCAPE;
 
-            final int displayId = mDisplayContent.getDisplayId();
-            final int appWidth = mService.mPolicy.getNonDecorDisplayWidth(dw, dh, rotation,
-                baseConfig.uiMode, displayId, displayCutout);
-            final int appHeight = mService.mPolicy.getNonDecorDisplayHeight(dw, dh, rotation,
-                baseConfig.uiMode, displayId, displayCutout);
-            mService.mPolicy.getNonDecorInsetsLw(rotation, dw, dh, displayCutout, mTmpRect);
+            final int appWidth = displayPolicy.getNonDecorDisplayWidth(dw, dh, rotation,
+                    baseConfig.uiMode, displayCutout);
+            final int appHeight = displayPolicy.getNonDecorDisplayHeight(dw, dh, rotation,
+                    baseConfig.uiMode, displayCutout);
+            displayPolicy.getNonDecorInsetsLw(rotation, dw, dh, displayCutout, mTmpRect);
             final int leftInset = mTmpRect.left;
             final int topInset = mTmpRect.top;
 
@@ -295,10 +299,10 @@
                     leftInset + appWidth /*right*/, topInset + appHeight /*bottom*/);
 
             final float density = mDisplayContent.getDisplayMetrics().density;
-            config.screenWidthDp = (int) (mService.mPolicy.getConfigDisplayWidth(dw, dh,
-                    rotation, baseConfig.uiMode, displayId, displayCutout) / density);
-            config.screenHeightDp = (int) (mService.mPolicy.getConfigDisplayHeight(dw, dh,
-                    rotation, baseConfig.uiMode, displayId, displayCutout) / density);
+            config.screenWidthDp = (int) (displayPolicy.getConfigDisplayWidth(dw, dh, rotation,
+                    baseConfig.uiMode, displayCutout) / density);
+            config.screenHeightDp = (int) (displayPolicy.getConfigDisplayHeight(dw, dh, rotation,
+                    baseConfig.uiMode, displayCutout) / density);
             final Context rotationContext = mService.mContext.createConfigurationContext(config);
             mSnapAlgorithmForRotation[rotation] = new DividerSnapAlgorithm(
                     rotationContext.getResources(), dw, dh, getContentWidth(),
@@ -464,8 +468,32 @@
      * @return true if the side provided is valid
      */
     boolean canPrimaryStackDockTo(int dockSide, Rect parentRect, int rotation) {
-        return mService.mPolicy.isDockSideAllowed(dockSide, mOriginalDockedSide,
-                parentRect.width(), parentRect.height(), rotation);
+        final DisplayPolicy policy = mDisplayContent.getDisplayPolicy();
+        return isDockSideAllowed(dockSide, mOriginalDockedSide,
+                policy.navigationBarPosition(parentRect.width(), parentRect.height(), rotation),
+                policy.navigationBarCanMove());
+    }
+
+    @VisibleForTesting
+    static boolean isDockSideAllowed(int dockSide, int originalDockSide, int navBarPosition,
+            boolean navigationBarCanMove) {
+        if (dockSide == DOCKED_TOP) {
+            return true;
+        }
+
+        if (navigationBarCanMove) {
+            // Only allow the dockside opposite to the nav bar position in landscape
+            return dockSide == DOCKED_LEFT && navBarPosition == NAV_BAR_RIGHT
+                    || dockSide == DOCKED_RIGHT && navBarPosition == NAV_BAR_LEFT;
+        }
+
+        // Side is the same as original side
+        if (dockSide == originalDockSide) {
+            return true;
+        }
+
+        // Only if original docked side was top in portrait will allow left for landscape
+        return dockSide == DOCKED_LEFT && originalDockSide == DOCKED_TOP;
     }
 
     void notifyDockedStackExistsChanged(boolean exists) {
diff --git a/services/core/java/com/android/server/policy/ImmersiveModeConfirmation.java b/services/core/java/com/android/server/wm/ImmersiveModeConfirmation.java
similarity index 81%
rename from services/core/java/com/android/server/policy/ImmersiveModeConfirmation.java
rename to services/core/java/com/android/server/wm/ImmersiveModeConfirmation.java
index 4aa2446..3d20501 100644
--- a/services/core/java/com/android/server/policy/ImmersiveModeConfirmation.java
+++ b/services/core/java/com/android/server/wm/ImmersiveModeConfirmation.java
@@ -1,5 +1,5 @@
 /*
- * Copyright (C) 2013 The Android Open Source Project
+ * Copyright (C) 2018 The Android Open Source Project
  *
  * Licensed under the Apache License, Version 2.0 (the "License");
  * you may not use this file except in compliance with the License.
@@ -14,10 +14,11 @@
  * limitations under the License.
  */
 
-package com.android.server.policy;
+package com.android.server.wm;
 
 import static android.app.ActivityManager.LOCK_TASK_MODE_LOCKED;
 import static android.app.ActivityManager.LOCK_TASK_MODE_NONE;
+import static android.view.Display.DEFAULT_DISPLAY;
 
 import android.animation.ArgbEvaluator;
 import android.animation.ValueAnimator;
@@ -32,16 +33,14 @@
 import android.os.Binder;
 import android.os.Handler;
 import android.os.IBinder;
+import android.os.Looper;
 import android.os.Message;
-import android.os.RemoteException;
-import android.os.ServiceManager;
 import android.os.UserHandle;
 import android.os.UserManager;
 import android.provider.Settings;
-import android.service.vr.IVrManager;
-import android.service.vr.IVrStateCallbacks;
 import android.util.DisplayMetrics;
 import android.util.Slog;
+import android.view.Display;
 import android.view.Gravity;
 import android.view.MotionEvent;
 import android.view.View;
@@ -55,7 +54,6 @@
 import android.widget.FrameLayout;
 
 import com.android.internal.R;
-import com.android.server.vr.VrManagerService;
 
 /**
  *  Helper to manage showing/hiding a confirmation prompt when the navigation bar is hidden
@@ -67,30 +65,34 @@
     private static final boolean DEBUG_SHOW_EVERY_TIME = false; // super annoying, use with caution
     private static final String CONFIRMED = "confirmed";
 
+    private static boolean sConfirmed;
+
     private final Context mContext;
     private final H mHandler;
     private final long mShowDelayMs;
     private final long mPanicThresholdMs;
     private final IBinder mWindowToken = new Binder();
 
-    private boolean mConfirmed;
     private ClingWindowView mClingWindow;
     private long mPanicTime;
     private WindowManager mWindowManager;
-    private int mCurrentUserId;
     // Local copy of vr mode enabled state, to avoid calling into VrManager with
     // the lock held.
-    boolean mVrModeEnabled = false;
+    private boolean mVrModeEnabled;
     private int mLockTaskState = LOCK_TASK_MODE_NONE;
 
-    public ImmersiveModeConfirmation(Context context) {
-        mContext = ActivityThread.currentActivityThread().getSystemUiContext();
-        mHandler = new H();
+    ImmersiveModeConfirmation(Context context, Looper looper, boolean vrModeEnabled) {
+        final Display display = context.getDisplay();
+        final Context uiContext = ActivityThread.currentActivityThread().getSystemUiContext();
+        mContext = display.getDisplayId() == DEFAULT_DISPLAY
+                ? uiContext : uiContext.createDisplayContext(display);
+        mHandler = new H(looper);
         mShowDelayMs = getNavBarExitDuration() * 3;
         mPanicThresholdMs = context.getResources()
                 .getInteger(R.integer.config_immersive_mode_confirmation_panic);
         mWindowManager = (WindowManager)
                 mContext.getSystemService(Context.WINDOW_SERVICE);
+        mVrModeEnabled = vrModeEnabled;
     }
 
     private long getNavBarExitDuration() {
@@ -98,57 +100,46 @@
         return exit != null ? exit.getDuration() : 0;
     }
 
-    public void loadSetting(int currentUserId) {
-        mConfirmed = false;
-        mCurrentUserId = currentUserId;
-        if (DEBUG) Slog.d(TAG, String.format("loadSetting() mCurrentUserId=%d", mCurrentUserId));
+    static boolean loadSetting(int currentUserId, Context context) {
+        final boolean wasConfirmed = sConfirmed;
+        sConfirmed = false;
+        if (DEBUG) Slog.d(TAG, String.format("loadSetting() currentUserId=%d", currentUserId));
         String value = null;
         try {
-            value = Settings.Secure.getStringForUser(mContext.getContentResolver(),
+            value = Settings.Secure.getStringForUser(context.getContentResolver(),
                     Settings.Secure.IMMERSIVE_MODE_CONFIRMATIONS,
                     UserHandle.USER_CURRENT);
-            mConfirmed = CONFIRMED.equals(value);
-            if (DEBUG) Slog.d(TAG, "Loaded mConfirmed=" + mConfirmed);
+            sConfirmed = CONFIRMED.equals(value);
+            if (DEBUG) Slog.d(TAG, "Loaded sConfirmed=" + sConfirmed);
         } catch (Throwable t) {
             Slog.w(TAG, "Error loading confirmations, value=" + value, t);
         }
+        return sConfirmed != wasConfirmed;
     }
 
-    private void saveSetting() {
+    private static void saveSetting(Context context) {
         if (DEBUG) Slog.d(TAG, "saveSetting()");
         try {
-            final String value = mConfirmed ? CONFIRMED : null;
-            Settings.Secure.putStringForUser(mContext.getContentResolver(),
+            final String value = sConfirmed ? CONFIRMED : null;
+            Settings.Secure.putStringForUser(context.getContentResolver(),
                     Settings.Secure.IMMERSIVE_MODE_CONFIRMATIONS,
                     value,
                     UserHandle.USER_CURRENT);
             if (DEBUG) Slog.d(TAG, "Saved value=" + value);
         } catch (Throwable t) {
-            Slog.w(TAG, "Error saving confirmations, mConfirmed=" + mConfirmed, t);
+            Slog.w(TAG, "Error saving confirmations, sConfirmed=" + sConfirmed, t);
         }
     }
 
-    void systemReady() {
-        IVrManager vrManager = IVrManager.Stub.asInterface(
-                ServiceManager.getService(Context.VR_SERVICE));
-        if (vrManager != null) {
-            try {
-                vrManager.registerListener(mVrStateCallbacks);
-                mVrModeEnabled = vrManager.getVrModeState();
-            } catch (RemoteException re) {
-            }
-        }
-    }
-
-    public void immersiveModeChangedLw(String pkg, boolean isImmersiveMode,
+    void immersiveModeChangedLw(String pkg, boolean isImmersiveMode,
             boolean userSetupComplete, boolean navBarEmpty) {
         mHandler.removeMessages(H.SHOW);
         if (isImmersiveMode) {
             final boolean disabled = PolicyControl.disableImmersiveConfirmation(pkg);
-            if (DEBUG) Slog.d(TAG, String.format("immersiveModeChanged() disabled=%s mConfirmed=%s",
-                    disabled, mConfirmed));
+            if (DEBUG) Slog.d(TAG, String.format("immersiveModeChanged() disabled=%s sConfirmed=%s",
+                    disabled, sConfirmed));
             if (!disabled
-                    && (DEBUG_SHOW_EVERY_TIME || !mConfirmed)
+                    && (DEBUG_SHOW_EVERY_TIME || !sConfirmed)
                     && userSetupComplete
                     && !mVrModeEnabled
                     && !navBarEmpty
@@ -161,7 +152,7 @@
         }
     }
 
-    public boolean onPowerKeyDown(boolean isScreenOn, long time, boolean inImmersiveMode,
+    boolean onPowerKeyDown(boolean isScreenOn, long time, boolean inImmersiveMode,
             boolean navBarEmpty) {
         if (!isScreenOn && (time - mPanicTime < mPanicThresholdMs)) {
             // turning the screen back on within the panic threshold
@@ -176,7 +167,7 @@
         return false;
     }
 
-    public void confirmCurrentPrompt() {
+    void confirmCurrentPrompt() {
         if (mClingWindow != null) {
             if (DEBUG) Slog.d(TAG, "confirmCurrentPrompt()");
             mHandler.post(mConfirm);
@@ -191,16 +182,14 @@
         }
     }
 
-    public WindowManager.LayoutParams getClingWindowLayoutParams() {
+    private WindowManager.LayoutParams getClingWindowLayoutParams() {
         final WindowManager.LayoutParams lp = new WindowManager.LayoutParams(
                 ViewGroup.LayoutParams.MATCH_PARENT,
                 ViewGroup.LayoutParams.MATCH_PARENT,
                 WindowManager.LayoutParams.TYPE_STATUS_BAR_PANEL,
-                0
-                        | WindowManager.LayoutParams.FLAG_LAYOUT_IN_SCREEN
+                WindowManager.LayoutParams.FLAG_LAYOUT_IN_SCREEN
                         | WindowManager.LayoutParams.FLAG_HARDWARE_ACCELERATED
-                        | WindowManager.LayoutParams.FLAG_NOT_TOUCH_MODAL
-                ,
+                        | WindowManager.LayoutParams.FLAG_NOT_TOUCH_MODAL,
                 PixelFormat.TRANSLUCENT);
         lp.privateFlags |= WindowManager.LayoutParams.PRIVATE_FLAG_SHOW_FOR_ALL_USERS;
         lp.setTitle("ImmersiveModeConfirmation");
@@ -209,7 +198,7 @@
         return lp;
     }
 
-    public FrameLayout.LayoutParams getBubbleLayoutParams() {
+    private FrameLayout.LayoutParams getBubbleLayoutParams() {
         return new FrameLayout.LayoutParams(
                 mContext.getResources().getDimensionPixelSize(
                         R.dimen.immersive_mode_cling_width),
@@ -220,7 +209,7 @@
     /**
      * @return the window token that's used by all ImmersiveModeConfirmation windows.
      */
-    public IBinder getWindowToken() {
+    IBinder getWindowToken() {
         return mWindowToken;
     }
 
@@ -272,7 +261,7 @@
             }
         };
 
-        public ClingWindowView(Context context, Runnable confirm) {
+        ClingWindowView(Context context, Runnable confirm) {
             super(context);
             mConfirm = confirm;
             setBackground(mColor);
@@ -295,7 +284,7 @@
             mClingLayout = (ViewGroup)
                     View.inflate(getContext(), R.layout.immersive_mode_cling, null);
 
-            final Button ok = (Button) mClingLayout.findViewById(R.id.ok);
+            final Button ok = mClingLayout.findViewById(R.id.ok);
             ok.setOnClickListener(new OnClickListener() {
                 @Override
                 public void onClick(View v) {
@@ -359,8 +348,7 @@
 
         // we will be hiding the nav bar, so layout as if it's already hidden
         mClingWindow.setSystemUiVisibility(
-                View.SYSTEM_UI_FLAG_LAYOUT_HIDE_NAVIGATION
-              | View.SYSTEM_UI_FLAG_LAYOUT_STABLE);
+                View.SYSTEM_UI_FLAG_LAYOUT_HIDE_NAVIGATION | View.SYSTEM_UI_FLAG_LAYOUT_STABLE);
 
         // show the confirmation
         WindowManager.LayoutParams lp = getClingWindowLayoutParams();
@@ -371,9 +359,9 @@
         @Override
         public void run() {
             if (DEBUG) Slog.d(TAG, "mConfirm.run()");
-            if (!mConfirmed) {
-                mConfirmed = true;
-                saveSetting();
+            if (!sConfirmed) {
+                sConfirmed = true;
+                saveSetting(mContext);
             }
             handleHide();
         }
@@ -383,6 +371,10 @@
         private static final int SHOW = 1;
         private static final int HIDE = 2;
 
+        H(Looper looper) {
+            super(looper);
+        }
+
         @Override
         public void handleMessage(Message msg) {
             switch(msg.what) {
@@ -396,16 +388,13 @@
         }
     }
 
-    private final IVrStateCallbacks mVrStateCallbacks = new IVrStateCallbacks.Stub() {
-        @Override
-        public void onVrStateChanged(boolean enabled) throws RemoteException {
-            mVrModeEnabled = enabled;
-            if (mVrModeEnabled) {
-                mHandler.removeMessages(H.SHOW);
-                mHandler.sendEmptyMessage(H.HIDE);
-            }
+    void onVrStateChangedLw(boolean enabled) {
+        mVrModeEnabled = enabled;
+        if (mVrModeEnabled) {
+            mHandler.removeMessages(H.SHOW);
+            mHandler.sendEmptyMessage(H.HIDE);
         }
-    };
+    }
 
     void onLockTaskModeChangedLw(int lockTaskState) {
         mLockTaskState = lockTaskState;
diff --git a/services/core/java/com/android/server/policy/NavigationBarExperiments.java b/services/core/java/com/android/server/wm/NavigationBarExperiments.java
similarity index 96%
rename from services/core/java/com/android/server/policy/NavigationBarExperiments.java
rename to services/core/java/com/android/server/wm/NavigationBarExperiments.java
index 06772e3..b74fb45 100644
--- a/services/core/java/com/android/server/policy/NavigationBarExperiments.java
+++ b/services/core/java/com/android/server/wm/NavigationBarExperiments.java
@@ -14,7 +14,7 @@
  * limitations under the License.
  */
 
-package com.android.server.policy;
+package com.android.server.wm;
 
 import static android.app.WindowConfiguration.ACTIVITY_TYPE_HOME;
 import static android.view.WindowManager.LayoutParams.TYPE_INPUT_METHOD;
@@ -25,9 +25,6 @@
 import android.content.Context;
 import android.graphics.Rect;
 
-import com.android.server.policy.WindowManagerPolicy.WindowState;
-import com.android.server.wm.WindowFrames;
-
 /**
  * This class acts as a proxy for Navigation Bar experiments enabled with custom overlays
  * {@see OverlayManagerService}. By default with no overlays, this class will essentially do nothing
diff --git a/services/core/java/com/android/server/wm/PinnedStackController.java b/services/core/java/com/android/server/wm/PinnedStackController.java
index d21f67d..ba23258 100644
--- a/services/core/java/com/android/server/wm/PinnedStackController.java
+++ b/services/core/java/com/android/server/wm/PinnedStackController.java
@@ -514,8 +514,9 @@
      */
     private void getInsetBounds(Rect outRect) {
         synchronized (mService.mGlobalLock) {
-            mService.mPolicy.getStableInsetsLw(mDisplayInfo.rotation, mDisplayInfo.logicalWidth,
-                    mDisplayInfo.logicalHeight, mDisplayInfo.displayCutout, mTmpInsets);
+            mDisplayContent.getDisplayPolicy().getStableInsetsLw(mDisplayInfo.rotation,
+                    mDisplayInfo.logicalWidth, mDisplayInfo.logicalHeight,
+                    mDisplayInfo.displayCutout, mTmpInsets);
             outRect.set(mTmpInsets.left + mScreenEdgeInsets.x, mTmpInsets.top + mScreenEdgeInsets.y,
                     mDisplayInfo.logicalWidth - mTmpInsets.right - mScreenEdgeInsets.x,
                     mDisplayInfo.logicalHeight - mTmpInsets.bottom - mScreenEdgeInsets.y);
diff --git a/services/core/java/com/android/server/policy/PolicyControl.java b/services/core/java/com/android/server/wm/PolicyControl.java
similarity index 92%
rename from services/core/java/com/android/server/policy/PolicyControl.java
rename to services/core/java/com/android/server/wm/PolicyControl.java
index 48e72bc..4c8ce9e 100644
--- a/services/core/java/com/android/server/policy/PolicyControl.java
+++ b/services/core/java/com/android/server/wm/PolicyControl.java
@@ -1,5 +1,5 @@
 /*
- * Copyright (C) 2014 The Android Open Source Project
+ * Copyright (C) 2018 The Android Open Source Project
  *
  * Licensed under the Apache License, Version 2.0 (the "License");
  * you may not use this file except in compliance with the License.
@@ -14,7 +14,7 @@
  * limitations under the License.
  */
 
-package com.android.server.policy;
+package com.android.server.wm;
 
 import android.app.ActivityManager;
 import android.content.Context;
@@ -26,8 +26,6 @@
 import android.view.WindowManager;
 import android.view.WindowManager.LayoutParams;
 
-import com.android.server.policy.WindowManagerPolicy.WindowState;
-
 import java.io.PrintWriter;
 import java.io.StringWriter;
 
@@ -49,9 +47,9 @@
  * Separate multiple name-value pairs with ':'
  *   e.g. "immersive.status=apps:immersive.preconfirms=*"
  */
-public class PolicyControl {
-    private static String TAG = "PolicyControl";
-    private static boolean DEBUG = false;
+class PolicyControl {
+    private static final String TAG = "PolicyControl";
+    private static final boolean DEBUG = false;
 
     private static final String NAME_IMMERSIVE_FULL = "immersive.full";
     private static final String NAME_IMMERSIVE_STATUS = "immersive.status";
@@ -63,7 +61,7 @@
     private static Filter sImmersiveStatusFilter;
     private static Filter sImmersiveNavigationFilter;
 
-    public static int getSystemUiVisibility(WindowState win, LayoutParams attrs) {
+    static int getSystemUiVisibility(WindowState win, LayoutParams attrs) {
         attrs = attrs != null ? attrs : win.getAttrs();
         int vis = win != null ? win.getSystemUiVisibility()
                 : (attrs.systemUiVisibility | attrs.subtreeSystemUiVisibility);
@@ -84,7 +82,7 @@
         return vis;
     }
 
-    public static int getWindowFlags(WindowState win, LayoutParams attrs) {
+    static int getWindowFlags(WindowState win, LayoutParams attrs) {
         attrs = attrs != null ? attrs : win.getAttrs();
         int flags = attrs.flags;
         if (sImmersiveStatusFilter != null && sImmersiveStatusFilter.matches(attrs)) {
@@ -98,7 +96,7 @@
         return flags;
     }
 
-    public static int adjustClearableFlags(WindowState win, int clearableFlags) {
+    static int adjustClearableFlags(WindowState win, int clearableFlags) {
         final LayoutParams attrs = win != null ? win.getAttrs() : null;
         if (sImmersiveStatusFilter != null && sImmersiveStatusFilter.matches(attrs)) {
             clearableFlags &= ~View.SYSTEM_UI_FLAG_FULLSCREEN;
@@ -106,28 +104,32 @@
         return clearableFlags;
     }
 
-    public static boolean disableImmersiveConfirmation(String pkg) {
+    static boolean disableImmersiveConfirmation(String pkg) {
         return (sImmersivePreconfirmationsFilter != null
                 && sImmersivePreconfirmationsFilter.matches(pkg))
                 || ActivityManager.isRunningInTestHarness();
     }
 
-    public static void reloadFromSetting(Context context) {
+    static boolean reloadFromSetting(Context context) {
         if (DEBUG) Slog.d(TAG, "reloadFromSetting()");
         String value = null;
         try {
             value = Settings.Global.getStringForUser(context.getContentResolver(),
                     Settings.Global.POLICY_CONTROL,
                     UserHandle.USER_CURRENT);
-            if (sSettingValue != null && sSettingValue.equals(value)) return;
+            if (sSettingValue == value || sSettingValue != null && sSettingValue.equals(value)) {
+                return false;
+            }
             setFilters(value);
             sSettingValue = value;
         } catch (Throwable t) {
             Slog.w(TAG, "Error loading policy control, value=" + value, t);
+            return false;
         }
+        return true;
     }
 
-    public static void dump(String prefix, PrintWriter pw) {
+    static void dump(String prefix, PrintWriter pw) {
         dump("sImmersiveStatusFilter", sImmersiveStatusFilter, prefix, pw);
         dump("sImmersiveNavigationFilter", sImmersiveNavigationFilter, prefix, pw);
         dump("sImmersivePreconfirmationsFilter", sImmersivePreconfirmationsFilter, prefix, pw);
diff --git a/services/core/java/com/android/server/wm/RootWindowContainer.java b/services/core/java/com/android/server/wm/RootWindowContainer.java
index 72e3562..b483fd3 100644
--- a/services/core/java/com/android/server/wm/RootWindowContainer.java
+++ b/services/core/java/com/android/server/wm/RootWindowContainer.java
@@ -120,13 +120,10 @@
     // events.
     int mTopFocusedDisplayId = INVALID_DISPLAY;
 
-    // Only a seperate transaction until we seperate the apply surface changes
+    // Only a separate transaction until we separate the apply surface changes
     // transaction from the global transaction.
     private final SurfaceControl.Transaction mDisplayTransaction = new SurfaceControl.Transaction();
 
-    private final Consumer<DisplayContent> mDisplayContentConfigChangesConsumer =
-            mService.mPolicy::onConfigurationChanged;
-
     private final Consumer<WindowState> mCloseSystemDialogsConsumer = w -> {
         if (w.mHasSurface) {
             try {
@@ -362,8 +359,6 @@
     public void onConfigurationChanged(Configuration newParentConfig) {
         prepareFreezingTaskBounds();
         super.onConfigurationChanged(newParentConfig);
-
-        forAllDisplays(mDisplayContentConfigChangesConsumer);
     }
 
     private void prepareFreezingTaskBounds() {
@@ -1052,6 +1047,12 @@
         }
     }
 
+    void forAllDisplayPolicies(Consumer<DisplayPolicy> callback) {
+        for (int i = mChildren.size() - 1; i >= 0; --i) {
+            callback.accept(mChildren.get(i).getDisplayPolicy());
+        }
+    }
+
     /**
      * Get current topmost focused IME window in system.
      * Will look on all displays in current Z-order.
diff --git a/services/core/java/com/android/server/wm/StackWindowController.java b/services/core/java/com/android/server/wm/StackWindowController.java
index baeedbc..35264a2 100644
--- a/services/core/java/com/android/server/wm/StackWindowController.java
+++ b/services/core/java/com/android/server/wm/StackWindowController.java
@@ -261,11 +261,12 @@
             final DisplayContent displayContent = stack.getDisplayContent();
             final DisplayInfo di = displayContent.getDisplayInfo();
             final DisplayCutout displayCutout = di.displayCutout;
+            final DisplayPolicy displayPolicy = displayContent.getDisplayPolicy();
 
             // Get the insets and display bounds
-            mService.mPolicy.getStableInsetsLw(di.rotation, di.logicalWidth, di.logicalHeight,
+            displayPolicy.getStableInsetsLw(di.rotation, di.logicalWidth, di.logicalHeight,
                     displayCutout, mTmpStableInsets);
-            mService.mPolicy.getNonDecorInsetsLw(di.rotation, di.logicalWidth, di.logicalHeight,
+            displayPolicy.getNonDecorInsetsLw(di.rotation, di.logicalWidth, di.logicalHeight,
                     displayCutout, mTmpNonDecorInsets);
             mTmpDisplayBounds.set(0, 0, di.logicalWidth, di.logicalHeight);
 
diff --git a/services/core/java/com/android/server/wm/StatusBarController.java b/services/core/java/com/android/server/wm/StatusBarController.java
new file mode 100644
index 0000000..b4de75b
--- /dev/null
+++ b/services/core/java/com/android/server/wm/StatusBarController.java
@@ -0,0 +1,113 @@
+/*
+ * Copyright (C) 2018 The Android Open Source Project
+ *
+ * Licensed under the Apache License, Version 2.0 (the "License");
+ * you may not use this file except in compliance with the License.
+ * You may obtain a copy of the License at
+ *
+ *      http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS,
+ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ * See the License for the specific language governing permissions and
+ * limitations under the License.
+ */
+
+package com.android.server.wm;
+
+import static android.view.WindowManager.LayoutParams.FLAG_TRANSLUCENT_STATUS;
+import static android.view.WindowManager.LayoutParams.MATCH_PARENT;
+
+import static com.android.server.wm.WindowManagerInternal.AppTransitionListener;
+
+import android.app.StatusBarManager;
+import android.os.IBinder;
+import android.view.View;
+
+import com.android.server.statusbar.StatusBarManagerInternal;
+
+/**
+ * Implements status bar specific behavior.
+ */
+public class StatusBarController extends BarController {
+
+    private final AppTransitionListener mAppTransitionListener = new AppTransitionListener() {
+
+        private Runnable mAppTransitionPending = () -> {
+            StatusBarManagerInternal statusBar = getStatusBarInternal();
+            if (statusBar != null && mWin != null) {
+                statusBar.appTransitionPending(mWin.getDisplayId());
+            }
+        };
+
+        private Runnable mAppTransitionCancelled = () -> {
+            StatusBarManagerInternal statusBar = getStatusBarInternal();
+            if (statusBar != null && mWin != null) {
+                statusBar.appTransitionCancelled(mWin.getDisplayId());
+            }
+        };
+
+        private Runnable mAppTransitionFinished = () -> {
+            StatusBarManagerInternal statusBar = getStatusBarInternal();
+            if (statusBar != null && mWin != null) {
+                statusBar.appTransitionFinished(mWin.getDisplayId());
+            }
+        };
+
+        @Override
+        public void onAppTransitionPendingLocked() {
+            mHandler.post(mAppTransitionPending);
+        }
+
+        @Override
+        public int onAppTransitionStartingLocked(int transit, IBinder openToken,
+                IBinder closeToken, long duration, long statusBarAnimationStartTime,
+                long statusBarAnimationDuration) {
+            mHandler.post(() -> {
+                StatusBarManagerInternal statusBar = getStatusBarInternal();
+                if (statusBar != null && mWin != null) {
+                    statusBar.appTransitionStarting(mWin.getDisplayId(),
+                            statusBarAnimationStartTime, statusBarAnimationDuration);
+                }
+            });
+            return 0;
+        }
+
+        @Override
+        public void onAppTransitionCancelledLocked(int transit) {
+            mHandler.post(mAppTransitionCancelled);
+        }
+
+        @Override
+        public void onAppTransitionFinishedLocked(IBinder token) {
+            mHandler.post(mAppTransitionFinished);
+        }
+    };
+
+    StatusBarController() {
+        super("StatusBar",
+                View.STATUS_BAR_TRANSIENT,
+                View.STATUS_BAR_UNHIDE,
+                View.STATUS_BAR_TRANSLUCENT,
+                StatusBarManager.WINDOW_STATUS_BAR,
+                FLAG_TRANSLUCENT_STATUS,
+                View.STATUS_BAR_TRANSPARENT);
+    }
+
+    void setTopAppHidesStatusBar(boolean hidesStatusBar) {
+        StatusBarManagerInternal statusBar = getStatusBarInternal();
+        if (statusBar != null) {
+            statusBar.setTopAppHidesStatusBar(hidesStatusBar);
+        }
+    }
+
+    @Override
+    protected boolean skipAnimation() {
+        return mWin.getAttrs().height == MATCH_PARENT;
+    }
+
+    AppTransitionListener getAppTransitionListener() {
+        return mAppTransitionListener;
+    }
+}
diff --git a/services/core/java/com/android/server/policy/SystemGesturesPointerEventListener.java b/services/core/java/com/android/server/wm/SystemGesturesPointerEventListener.java
similarity index 93%
rename from services/core/java/com/android/server/policy/SystemGesturesPointerEventListener.java
rename to services/core/java/com/android/server/wm/SystemGesturesPointerEventListener.java
index d3cc8ef..bdb76c2 100644
--- a/services/core/java/com/android/server/policy/SystemGesturesPointerEventListener.java
+++ b/services/core/java/com/android/server/wm/SystemGesturesPointerEventListener.java
@@ -1,5 +1,5 @@
 /*
- * Copyright (C) 2013 The Android Open Source Project
+ * Copyright (C) 2018 The Android Open Source Project
  *
  * Licensed under the Apache License, Version 2.0 (the "License");
  * you may not use this file except in compliance with the License.
@@ -14,11 +14,10 @@
  * limitations under the License.
  */
 
-package com.android.server.policy;
+package com.android.server.wm;
 
 import android.content.Context;
 import android.os.Handler;
-import android.os.Looper;
 import android.os.SystemClock;
 import android.util.Slog;
 import android.view.GestureDetector;
@@ -27,11 +26,11 @@
 import android.view.WindowManagerPolicyConstants.PointerEventListener;
 import android.widget.OverScroller;
 
-/*
+/**
  * Listens for system-wide input gestures, firing callbacks when detected.
  * @hide
  */
-public class SystemGesturesPointerEventListener implements PointerEventListener {
+class SystemGesturesPointerEventListener implements PointerEventListener {
     private static final String TAG = "SystemGestures";
     private static final boolean DEBUG = false;
     private static final long SWIPE_TIMEOUT_MS = 500;
@@ -46,6 +45,7 @@
     private static final int SWIPE_FROM_LEFT = 4;
 
     private final Context mContext;
+    private final Handler mHandler;
     private final int mSwipeStartThreshold;
     private final int mSwipeDistanceThreshold;
     private final Callbacks mCallbacks;
@@ -55,7 +55,6 @@
     private final long[] mDownTime = new long[MAX_TRACKED_POINTERS];
 
     private GestureDetector mGestureDetector;
-    private OverScroller mOverscroller;
 
     int screenHeight;
     int screenWidth;
@@ -65,8 +64,9 @@
     private boolean mMouseHoveringAtEdge;
     private long mLastFlingTime;
 
-    public SystemGesturesPointerEventListener(Context context, Callbacks callbacks) {
+    SystemGesturesPointerEventListener(Context context, Handler handler, Callbacks callbacks) {
         mContext = context;
+        mHandler = handler;
         mCallbacks = checkNull("callbacks", callbacks);
         mSwipeStartThreshold = checkNull("context", context).getResources()
                 .getDimensionPixelSize(com.android.internal.R.dimen.status_bar_height);
@@ -83,9 +83,7 @@
     }
 
     public void systemReady() {
-        Handler h = new Handler(Looper.myLooper());
-        mGestureDetector = new GestureDetector(mContext, new FlingGestureDetector(), h);
-        mOverscroller = new OverScroller(mContext);
+        mGestureDetector = new GestureDetector(mContext, new FlingGestureDetector(), mHandler);
     }
 
     @Override
@@ -163,14 +161,14 @@
     private void captureDown(MotionEvent event, int pointerIndex) {
         final int pointerId = event.getPointerId(pointerIndex);
         final int i = findIndex(pointerId);
-        if (DEBUG) Slog.d(TAG, "pointer " + pointerId +
-                " down pointerIndex=" + pointerIndex + " trackingIndex=" + i);
+        if (DEBUG) Slog.d(TAG, "pointer " + pointerId
+                + " down pointerIndex=" + pointerIndex + " trackingIndex=" + i);
         if (i != UNTRACKED_POINTER) {
             mDownX[i] = event.getX(pointerIndex);
             mDownY[i] = event.getY(pointerIndex);
             mDownTime[i] = event.getEventTime();
-            if (DEBUG) Slog.d(TAG, "pointer " + pointerId +
-                    " down x=" + mDownX[i] + " y=" + mDownY[i]);
+            if (DEBUG) Slog.d(TAG, "pointer " + pointerId
+                    + " down x=" + mDownX[i] + " y=" + mDownY[i]);
         }
     }
 
@@ -242,6 +240,13 @@
     }
 
     private final class FlingGestureDetector extends GestureDetector.SimpleOnGestureListener {
+
+        private OverScroller mOverscroller;
+
+        FlingGestureDetector() {
+            mOverscroller = new OverScroller(mContext);
+        }
+
         @Override
         public boolean onSingleTapUp(MotionEvent e) {
             if (!mOverscroller.isFinished()) {
diff --git a/services/core/java/com/android/server/wm/TaskStack.java b/services/core/java/com/android/server/wm/TaskStack.java
index 15de1ec..64f4ba5 100644
--- a/services/core/java/com/android/server/wm/TaskStack.java
+++ b/services/core/java/com/android/server/wm/TaskStack.java
@@ -521,7 +521,7 @@
         // Snap the position to a target.
         final int rotation = parentConfig.windowConfiguration.getRotation();
         final int orientation = parentConfig.orientation;
-        mService.mPolicy.getStableInsetsLw(rotation, displayWidth, displayHeight,
+        mDisplayContent.getDisplayPolicy().getStableInsetsLw(rotation, displayWidth, displayHeight,
                 displayCutout, outBounds);
         final DividerSnapAlgorithm algorithm = new DividerSnapAlgorithm(
                 mService.mContext.getResources(), displayWidth, displayHeight,
@@ -867,7 +867,8 @@
             // and its bounds can be adjusted after that. The bounds of all other stacks are
             // adjusted to occupy whatever screen space the docked stack isn't occupying.
             final DisplayCutout displayCutout = mDisplayContent.getDisplayInfo().displayCutout;
-            mService.mPolicy.getStableInsetsLw(parentConfig.windowConfiguration.getRotation(),
+            mDisplayContent.getDisplayPolicy().getStableInsetsLw(
+                    parentConfig.windowConfiguration.getRotation(),
                     displayRect.width(), displayRect.height(), displayCutout, mTmpRect2);
             final int position = new DividerSnapAlgorithm(mService.mContext.getResources(),
                     displayRect.width(),
diff --git a/services/core/java/com/android/server/wm/WindowManagerInternal.java b/services/core/java/com/android/server/wm/WindowManagerInternal.java
index b096bf2..e83b863 100644
--- a/services/core/java/com/android/server/wm/WindowManagerInternal.java
+++ b/services/core/java/com/android/server/wm/WindowManagerInternal.java
@@ -392,11 +392,6 @@
     public abstract boolean isStackVisible(int windowingMode);
 
     /**
-     * @return True if and only if the docked divider is currently in resize mode.
-     */
-    public abstract boolean isDockedDividerResizing();
-
-    /**
      * Requests the window manager to resend the windows for accessibility.
      */
     public abstract void computeWindowsForAccessibility();
diff --git a/services/core/java/com/android/server/wm/WindowManagerService.java b/services/core/java/com/android/server/wm/WindowManagerService.java
index 8d5cd78..39a8465 100644
--- a/services/core/java/com/android/server/wm/WindowManagerService.java
+++ b/services/core/java/com/android/server/wm/WindowManagerService.java
@@ -171,6 +171,8 @@
 import android.os.UserHandle;
 import android.os.WorkSource;
 import android.provider.Settings;
+import android.service.vr.IVrManager;
+import android.service.vr.IVrStateCallbacks;
 import android.text.format.DateUtils;
 import android.util.ArrayMap;
 import android.util.ArraySet;
@@ -231,6 +233,7 @@
 import com.android.internal.util.DumpUtils;
 import com.android.internal.util.FastPrintWriter;
 import com.android.internal.util.LatencyTracker;
+import com.android.internal.util.function.pooled.PooledLambda;
 import com.android.internal.view.WindowManagerPolicyThread;
 import com.android.server.AnimationThread;
 import com.android.server.DisplayThread;
@@ -373,6 +376,18 @@
     boolean mKeyguardOrAodShowingOnDefaultDisplay;
     // VR Vr2d Display Id.
     int mVr2dDisplayId = INVALID_DISPLAY;
+    boolean mVrModeEnabled = false;
+
+    private final IVrStateCallbacks mVrStateCallbacks = new IVrStateCallbacks.Stub() {
+        @Override
+        public void onVrStateChanged(boolean enabled) {
+            synchronized (mGlobalLock) {
+                mVrModeEnabled = enabled;
+                mRoot.forAllDisplayPolicies(PooledLambda.obtainConsumer(
+                        DisplayPolicy::onVrStateChangedLw, PooledLambda.__(), enabled));
+            }
+        }
+    };
 
     private final BroadcastReceiver mBroadcastReceiver = new BroadcastReceiver() {
         @Override
@@ -528,6 +543,7 @@
     boolean mForceDisplayEnabled = false;
     boolean mShowingBootMessages = false;
     boolean mBootAnimationStopped = false;
+    boolean mSystemReady = false;
 
     // Following variables are for debugging screen wakelock only.
     WindowState mLastWakeLockHoldingWindow = null;
@@ -579,9 +595,6 @@
     final WallpaperVisibilityListeners mWallpaperVisibilityListeners =
             new WallpaperVisibilityListeners();
 
-    int mSystemDecorLayer = 0;
-    final Rect mScreenRect = new Rect();
-
     boolean mDisplayFrozen = false;
     long mDisplayFreezeTime = 0;
     int mLastDisplayFreezeDuration = 0;
@@ -597,11 +610,6 @@
     boolean mClientFreezingScreen = false;
     int mAppsFreezingScreen = 0;
 
-    // Last systemUiVisibility we received from status bar.
-    int mLastStatusBarVisibility = 0;
-    // Last systemUiVisibility we dispatched to windows.
-    int mLastDispatchedSystemUiVisibility = 0;
-
     // State while inside of layoutAndPlaceSurfacesLocked().
     boolean mFocusMayChange;
 
@@ -649,6 +657,10 @@
                 Settings.Global.getUriFor(Settings.Global.TRANSITION_ANIMATION_SCALE);
         private final Uri mAnimationDurationScaleUri =
                 Settings.Global.getUriFor(Settings.Global.ANIMATOR_DURATION_SCALE);
+        private final Uri mImmersiveModeConfirmationsUri =
+                Settings.Secure.getUriFor(Settings.Secure.IMMERSIVE_MODE_CONFIRMATIONS);
+        private final Uri mPolicyControlUri =
+                Settings.Global.getUriFor(Settings.Global.POLICY_CONTROL);
 
         public SettingsObserver() {
             super(new Handler());
@@ -661,6 +673,10 @@
                     UserHandle.USER_ALL);
             resolver.registerContentObserver(mAnimationDurationScaleUri, false, this,
                     UserHandle.USER_ALL);
+            resolver.registerContentObserver(mImmersiveModeConfirmationsUri, false, this,
+                    UserHandle.USER_ALL);
+            resolver.registerContentObserver(mPolicyControlUri, false, this,
+                    UserHandle.USER_ALL);
         }
 
         @Override
@@ -669,23 +685,40 @@
                 return;
             }
 
+            if (mImmersiveModeConfirmationsUri.equals(uri) || mPolicyControlUri.equals(uri)) {
+                updateSystemUiSettings();
+                return;
+            }
+
             if (mDisplayInversionEnabledUri.equals(uri)) {
                 updateCircularDisplayMaskIfNeeded();
+                return;
+            }
+
+            @UpdateAnimationScaleMode
+            final int mode;
+            if (mWindowAnimationScaleUri.equals(uri)) {
+                mode = WINDOW_ANIMATION_SCALE;
+            } else if (mTransitionAnimationScaleUri.equals(uri)) {
+                mode = TRANSITION_ANIMATION_SCALE;
+            } else if (mAnimationDurationScaleUri.equals(uri)) {
+                mode = ANIMATION_DURATION_SCALE;
             } else {
-                @UpdateAnimationScaleMode
-                final int mode;
-                if (mWindowAnimationScaleUri.equals(uri)) {
-                    mode = WINDOW_ANIMATION_SCALE;
-                } else if (mTransitionAnimationScaleUri.equals(uri)) {
-                    mode = TRANSITION_ANIMATION_SCALE;
-                } else if (mAnimationDurationScaleUri.equals(uri)) {
-                    mode = ANIMATION_DURATION_SCALE;
-                } else {
-                    // Ignoring unrecognized content changes
-                    return;
-                }
-                Message m = mH.obtainMessage(H.UPDATE_ANIMATION_SCALE, mode, 0);
-                mH.sendMessage(m);
+                // Ignoring unrecognized content changes
+                return;
+            }
+            Message m = mH.obtainMessage(H.UPDATE_ANIMATION_SCALE, mode, 0);
+            mH.sendMessage(m);
+        }
+
+        void updateSystemUiSettings() {
+            boolean changed;
+            synchronized (mWindowMap) {
+                changed = ImmersiveModeConfirmation.loadSetting(mCurrentUserId, mContext)
+                        || PolicyControl.reloadFromSetting(mContext);
+            }
+            if (changed) {
+                updateRotation(false /* alwaysSendConfiguration */, false /* forceRelayout */);
             }
         }
     }
@@ -1286,10 +1319,11 @@
             final boolean hasStatusBarServicePermission =
                     mContext.checkCallingOrSelfPermission(permission.STATUS_BAR_SERVICE)
                             == PackageManager.PERMISSION_GRANTED;
-            mPolicy.adjustWindowParamsLw(win, win.mAttrs, hasStatusBarServicePermission);
+            final DisplayPolicy displayPolicy = displayContent.getDisplayPolicy();
+            displayPolicy.adjustWindowParamsLw(win, win.mAttrs, hasStatusBarServicePermission);
             win.setShowToOwnerOnlyLocked(mPolicy.checkShowToOwnerOnly(attrs));
 
-            res = mPolicy.prepareAddWindowLw(win, attrs);
+            res = displayPolicy.prepareAddWindowLw(win, attrs);
             if (res != WindowManagerGlobal.ADD_OKAY) {
                 return res;
             }
@@ -1422,9 +1456,8 @@
                 taskBounds = null;
                 floatingStack = false;
             }
-            if (mPolicy.getLayoutHintLw(win.mAttrs, taskBounds, displayFrames, floatingStack,
-                    outFrame, outContentInsets, outStableInsets, outOutsets,
-                    outDisplayCutout)) {
+            if (displayPolicy.getLayoutHintLw(win.mAttrs, taskBounds, displayFrames, floatingStack,
+                    outFrame, outContentInsets, outStableInsets, outOutsets, outDisplayCutout)) {
                 res |= WindowManagerGlobal.ADD_FLAG_ALWAYS_CONSUME_NAV_BAR;
             }
 
@@ -1842,6 +1875,8 @@
                 return 0;
             }
             displayId = win.getDisplayId();
+            final DisplayContent displayContent = win.getDisplayContent();
+            final DisplayPolicy displayPolicy = displayContent.getDisplayPolicy();
 
             WindowStateAnimator winAnimator = win.mWinAnimator;
             if (viewVisibility != View.GONE) {
@@ -1857,7 +1892,7 @@
             int attrChanges = 0;
             int flagChanges = 0;
             if (attrs != null) {
-                mPolicy.adjustWindowParamsLw(win, attrs, hasStatusBarServicePermission);
+                displayPolicy.adjustWindowParamsLw(win, attrs, hasStatusBarServicePermission);
                 // if they don't have the permission, mask out the status bar bits
                 if (seq == win.mSeq) {
                     int systemUiVisibility = attrs.systemUiVisibility
@@ -1996,7 +2031,7 @@
                 try {
                     result = createSurfaceControl(outSurface, result, win, winAnimator);
                 } catch (Exception e) {
-                    win.getDisplayContent().getInputMonitor().updateInputWindowsLw(true /*force*/);
+                    displayContent.getInputMonitor().updateInputWindowsLw(true /*force*/);
 
                     Slog.w(TAG_WM, "Exception thrown when creating surface for client "
                              + client + " (" + win.mAttrs.getTitle() + ")",
@@ -2007,7 +2042,6 @@
                 if ((result & WindowManagerGlobal.RELAYOUT_RES_FIRST_TIME) != 0) {
                     focusMayChange = true;
                 }
-                final DisplayContent displayContent = win.getDisplayContent();
                 if (win.mAttrs.type == TYPE_INPUT_METHOD
                         && displayContent.mInputMethodWindow == null) {
                     displayContent.setInputMethodWindowLocked(win);
@@ -2052,35 +2086,34 @@
             // updateFocusedWindowLocked() already assigned layers so we only need to
             // reassign them at this point if the IM window state gets shuffled
             boolean toBeDisplayed = (result & WindowManagerGlobal.RELAYOUT_RES_FIRST_TIME) != 0;
-            final DisplayContent dc = win.getDisplayContent();
             if (imMayMove) {
-                dc.computeImeTarget(true /* updateImeTarget */);
+                displayContent.computeImeTarget(true /* updateImeTarget */);
                 if (toBeDisplayed) {
                     // Little hack here -- we -should- be able to rely on the function to return
                     // true if the IME has moved and needs its layer recomputed. However, if the IME
                     // was hidden and isn't actually moved in the list, its layer may be out of data
                     // so we make sure to recompute it.
-                    dc.assignWindowLayers(false /* setLayoutNeeded */);
+                    displayContent.assignWindowLayers(false /* setLayoutNeeded */);
                 }
             }
 
             if (wallpaperMayMove) {
-                win.getDisplayContent().pendingLayoutChanges |=
+                displayContent.pendingLayoutChanges |=
                         WindowManagerPolicy.FINISH_LAYOUT_REDO_WALLPAPER;
             }
 
             if (win.mAppToken != null) {
-                dc.mUnknownAppVisibilityController.notifyRelayouted(win.mAppToken);
+                displayContent.mUnknownAppVisibilityController.notifyRelayouted(win.mAppToken);
             }
 
             Trace.traceBegin(TRACE_TAG_WINDOW_MANAGER,
                     "relayoutWindow: updateOrientationFromAppTokens");
-            configChanged = dc.updateOrientationFromAppTokens();
+            configChanged = displayContent.updateOrientationFromAppTokens();
             Trace.traceEnd(TRACE_TAG_WINDOW_MANAGER);
 
             if (toBeDisplayed && win.mIsWallpaper) {
-                DisplayInfo displayInfo = win.getDisplayContent().getDisplayInfo();
-                dc.mWallpaperController.updateWallpaperOffset(
+                DisplayInfo displayInfo = displayContent.getDisplayInfo();
+                displayContent.mWallpaperController.updateWallpaperOffset(
                         win, displayInfo.logicalWidth, displayInfo.logicalHeight, false);
             }
             if (win.mAppToken != null) {
@@ -2090,7 +2123,7 @@
                 winAnimator.mReportSurfaceResized = false;
                 result |= WindowManagerGlobal.RELAYOUT_RES_SURFACE_RESIZED;
             }
-            if (mPolicy.isNavBarForcedShownLw(win)) {
+            if (displayPolicy.isNavBarForcedShownLw(win)) {
                 result |= WindowManagerGlobal.RELAYOUT_RES_CONSUME_ALWAYS_NAV_BAR;
             }
             if (!win.isGoneForLayoutLw()) {
@@ -2408,7 +2441,7 @@
                 mWaitingForConfig = true;
                 displayContent.setLayoutNeeded();
                 int anim[] = new int[2];
-                mPolicy.selectRotationAnimationLw(anim);
+                displayContent.getDisplayPolicy().selectRotationAnimationLw(anim);
 
                 startFreezingDisplayLocked(anim[0], anim[1], displayContent);
                 config = new Configuration(mTempConfiguration);
@@ -2603,7 +2636,9 @@
         }
     }
 
-    @Override
+    /**
+     * Notifies window manager that {@link DisplayPolicy#isShowingDreamLw} has changed.
+     */
     public void notifyShowingDreamChanged() {
         // TODO(multi-display): support show dream in multi-display.
         notifyKeyguardFlagsChanged(null /* callback */, DEFAULT_DISPLAY);
@@ -2634,6 +2669,21 @@
         mH.sendEmptyMessage(H.RECOMPUTE_FOCUS);
     }
 
+    @Override
+    public void onPowerKeyDown(boolean isScreenOn) {
+        mRoot.forAllDisplayPolicies(PooledLambda.obtainConsumer(
+                DisplayPolicy::onPowerKeyDown, PooledLambda.__(), isScreenOn));
+    }
+
+    @Override
+    public void onUserSwitched() {
+        mSettingsObserver.updateSystemUiSettings();
+        synchronized (mWindowMap) {
+            // force a re-application of focused window sysui visibility on each display.
+            mRoot.forAllDisplayPolicies(DisplayPolicy::resetSystemUiVisibilityLw);
+        }
+    }
+
     /**
      * Starts deferring layout passes. Useful when doing multiple changes but to optimize
      * performance, only one layout pass should be done. This can be called multiple times, and
@@ -2839,7 +2889,8 @@
 
     public boolean isShowingDream() {
         synchronized (mGlobalLock) {
-            return mPolicy.isShowingDreamLw();
+            // TODO: fix this when dream can be shown on non-default display.
+            return getDefaultDisplayContentLocked().getDisplayPolicy().isShowingDreamLw();
         }
     }
 
@@ -3672,13 +3723,6 @@
     }
 
     @Override
-    public WindowManagerPolicy.DisplayContentInfo getDefaultDisplayContentInfo() {
-        synchronized (mGlobalLock) {
-            return getDefaultDisplayContentLocked();
-        }
-    }
-
-    @Override
     public int getDefaultDisplayRotation() {
         synchronized (mGlobalLock) {
             return getDefaultDisplayContentLocked().getRotation();
@@ -4291,10 +4335,29 @@
     }
 
     public void systemReady() {
+        mSystemReady = true;
         mPolicy.systemReady();
+        mRoot.forAllDisplayPolicies(DisplayPolicy::systemReady);
         mTaskSnapshotController.systemReady();
         mHasWideColorGamutSupport = queryWideColorGamutSupport();
         mHasHdrSupport = queryHdrSupport();
+        UiThread.getHandler().post(mSettingsObserver::updateSystemUiSettings);
+        IVrManager vrManager = IVrManager.Stub.asInterface(
+                ServiceManager.getService(Context.VR_SERVICE));
+        if (vrManager != null) {
+            try {
+                final boolean vrModeEnabled = vrManager.getVrModeState();
+                synchronized (mGlobalLock) {
+                    vrManager.registerListener(mVrStateCallbacks);
+                    if (vrModeEnabled) {
+                        mVrModeEnabled = vrModeEnabled;
+                        mVrStateCallbacks.onVrStateChanged(vrModeEnabled);
+                    }
+                }
+            } catch (RemoteException e) {
+                // Ignore, we cannot do anything if we failed to register VR mode listener
+            }
+        }
     }
 
     private static boolean queryWideColorGamutSupport() {
@@ -5382,7 +5445,8 @@
             if (DEBUG_ORIENTATION) Slog.i(TAG_WM, "**** Dismissing screen rotation animation");
             DisplayInfo displayInfo = displayContent.getDisplayInfo();
             // Get rotation animation again, with new top window
-            if (!mPolicy.validateRotationAnimationLw(mExitAnimId, mEnterAnimId, false)) {
+            if (!displayContent.getDisplayPolicy()
+                    .validateRotationAnimationLw(mExitAnimId, mEnterAnimId, false)) {
                 mExitAnimId = mEnterAnimId = 0;
             }
             if (screenRotationAnimation.dismiss(mTransaction, MAX_ANIMATION_DURATION,
@@ -5522,7 +5586,7 @@
     }
 
     @Override
-    public void statusBarVisibilityChanged(int visibility) {
+    public void statusBarVisibilityChanged(int displayId, int visibility) {
         if (mContext.checkCallingOrSelfPermission(android.Manifest.permission.STATUS_BAR)
                 != PackageManager.PERMISSION_GRANTED) {
             throw new SecurityException("Caller does not hold permission "
@@ -5530,9 +5594,12 @@
         }
 
         synchronized (mGlobalLock) {
-            mLastStatusBarVisibility = visibility;
-            visibility = mPolicy.adjustSystemUiVisibilityLw(visibility);
-            updateStatusBarVisibilityLocked(visibility);
+            final DisplayContent displayContent = mRoot.getDisplayContent(displayId);
+            if (displayContent != null) {
+                displayContent.statusBarVisibilityChanged(visibility);
+            } else {
+                Slog.w(TAG, "statusBarVisibilityChanged with invalid displayId=" + displayId);
+            }
         }
     }
 
@@ -5548,49 +5615,36 @@
         }
     }
 
-    // TODO(multidisplay): StatusBar on multiple screens?
-    private boolean updateStatusBarVisibilityLocked(int visibility) {
-        if (mLastDispatchedSystemUiVisibility == visibility) {
-            return false;
-        }
-        final int globalDiff = (visibility ^ mLastDispatchedSystemUiVisibility)
-                // We are only interested in differences of one of the
-                // clearable flags...
-                & View.SYSTEM_UI_CLEARABLE_FLAGS
-                // ...if it has actually been cleared.
-                & ~visibility;
-
-        mLastDispatchedSystemUiVisibility = visibility;
-        mInputManager.setSystemUiVisibility(visibility);
-        getDefaultDisplayContentLocked().updateSystemUiVisibility(visibility, globalDiff);
-        return true;
-    }
-
+    // TODO: Make the callers use getNavBarPosition(int) only.
+    /**
+     * Used by SystemUI and shared SystemUI libraries.
+     * @see DisplayPolicy#getNavBarPosition()
+     */
     @Override
-    public void reevaluateStatusBarVisibility() {
-        synchronized (mGlobalLock) {
-            int visibility = mPolicy.adjustSystemUiVisibilityLw(mLastStatusBarVisibility);
-            if (updateStatusBarVisibilityLocked(visibility)) {
-                mWindowPlacerLocked.requestTraversal();
-            }
-        }
+    @WindowManagerPolicy.NavigationBarPosition
+    public int getNavBarPosition() {
+        return getNavBarPosition(Display.DEFAULT_DISPLAY);
     }
 
     /**
      * Used by ActivityManager to determine where to position an app with aspect ratio shorter then
      * the screen is.
-     * @see WindowManagerPolicy#getNavBarPosition()
+     * @see DisplayPolicy#getNavBarPosition()
      */
-    @Override
     @WindowManagerPolicy.NavigationBarPosition
-    public int getNavBarPosition() {
+    public int getNavBarPosition(int displayId) {
         synchronized (mGlobalLock) {
             // Perform layout if it was scheduled before to make sure that we get correct nav bar
             // position when doing rotations.
-            final DisplayContent defaultDisplayContent = getDefaultDisplayContentLocked();
-            defaultDisplayContent.performLayout(false /* initial */,
+            final DisplayContent displayContent = mRoot.getDisplayContent(displayId);
+            if (displayContent == null) {
+                Slog.w(TAG, "getNavBarPosition with invalid displayId=" + displayId
+                        + " callers=" + Debug.getCallers(3));
+                return -1;
+            }
+            displayContent.performLayout(false /* initial */,
                     false /* updateInputWindows */);
-            return mPolicy.getNavBarPosition();
+            return displayContent.getDisplayPolicy().getNavBarPosition();
         }
     }
 
@@ -5776,11 +5830,6 @@
         }
     }
 
-    @Override
-    public int getDockedDividerInsetsLw() {
-        return getDefaultDisplayContentLocked().getDockedDividerController().getContentInsets();
-    }
-
     private void dumpPolicyLocked(PrintWriter pw, String[] args, boolean dumpAll) {
         pw.println("WINDOW MANAGER POLICY STATE (dumpsys window policy)");
         mPolicy.dump("    ", pw, args);
@@ -5969,12 +6018,6 @@
         mTaskSnapshotController.dump(pw, "  ");
 
         if (dumpAll) {
-            pw.print("  mSystemDecorLayer="); pw.print(mSystemDecorLayer);
-                    pw.print(" mScreenRect="); pw.println(mScreenRect.toShortString());
-            if (mLastStatusBarVisibility != 0) {
-                pw.print("  mLastStatusBarVisibility=0x");
-                        pw.println(Integer.toHexString(mLastStatusBarVisibility));
-            }
             final WindowState imeWindow = mRoot.getCurrentInputMethodWindow();
             if (imeWindow != null) {
                 pw.print("  mInputMethodWindow="); pw.println(imeWindow);
@@ -6007,6 +6050,7 @@
                 pw.print("  mRecentsAnimationController="); pw.println(mRecentsAnimationController);
                 mRecentsAnimationController.dump(pw, "    ");
             }
+            PolicyControl.dump("  ", pw);
         }
     }
 
@@ -6270,7 +6314,7 @@
     public void onOverlayChanged() {
         synchronized (mGlobalLock) {
             mRoot.forAllDisplays(displayContent -> {
-                mPolicy.onOverlayChangedLw(displayContent);
+                displayContent.getDisplayPolicy().onOverlayChangedLw();
                 displayContent.updateDisplayInfo();
             });
             requestTraversal();
@@ -6500,7 +6544,7 @@
         final DisplayContent dc = mRoot.getDisplayContent(displayId);
         if (dc != null) {
             final DisplayInfo di = dc.getDisplayInfo();
-            mPolicy.getStableInsetsLw(di.rotation, di.logicalWidth, di.logicalHeight,
+            dc.getDisplayPolicy().getStableInsetsLw(di.rotation, di.logicalWidth, di.logicalHeight,
                     di.displayCutout, outInsets);
         }
     }
@@ -7102,13 +7146,6 @@
         }
 
         @Override
-        public boolean isDockedDividerResizing() {
-            synchronized (mGlobalLock) {
-                return getDefaultDisplayContentLocked().getDockedDividerController().isResizing();
-            }
-        }
-
-        @Override
         public void computeWindowsForAccessibility() {
             final AccessibilityController accessibilityController;
             synchronized (mGlobalLock) {
@@ -7367,9 +7404,11 @@
      *                      {@link ActivityManager#LOCK_TASK_MODE_LOCKED},
      *                      {@link ActivityManager#LOCK_TASK_MODE_PINNED}.
      */
-    public void onLockTaskStateChanged(int lockTaskState) {
+    void onLockTaskStateChanged(int lockTaskState) {
+        // TODO: pass in displayId to determine which display the lock task state changed
         synchronized (mGlobalLock) {
-            mPolicy.onLockTaskStateChangedLw(lockTaskState);
+            mRoot.forAllDisplayPolicies(PooledLambda.obtainConsumer(
+                    DisplayPolicy::onLockTaskStateChangedLw, PooledLambda.__(), lockTaskState));
         }
     }
 
diff --git a/services/core/java/com/android/server/wm/WindowState.java b/services/core/java/com/android/server/wm/WindowState.java
index a117cf3..567b583 100644
--- a/services/core/java/com/android/server/wm/WindowState.java
+++ b/services/core/java/com/android/server/wm/WindowState.java
@@ -179,6 +179,7 @@
 import android.view.InputChannel;
 import android.view.InputEvent;
 import android.view.InputEventReceiver;
+import android.view.InputWindowHandle;
 import android.view.SurfaceControl;
 import android.view.SurfaceSession;
 import android.view.View;
@@ -191,7 +192,6 @@
 
 import com.android.internal.annotations.VisibleForTesting;
 import com.android.internal.util.ToBooleanFunction;
-import android.view.InputWindowHandle;
 import com.android.server.policy.WindowManagerPolicy;
 import com.android.server.wm.LocalAnimationAdapter.AnimationSpec;
 import com.android.server.wm.utils.InsetUtils;
@@ -1800,7 +1800,7 @@
             // also been registered in display.
             dc.mTapExcludeProvidingWindows.remove(this);
         }
-        mPolicy.removeWindowLw(this);
+        dc.getDisplayPolicy().removeWindowLw(this);
 
         disposeInputChannel();
 
@@ -2982,7 +2982,7 @@
 
         mClient.resized(frame, overscanInsets, contentInsets, visibleInsets, stableInsets, outsets,
                 reportDraw, mergedConfiguration, getBackdropFrame(frame), forceRelayout,
-                mPolicy.isNavBarForcedShownLw(this), displayId,
+                getDisplayContent().getDisplayPolicy().isNavBarForcedShownLw(this), displayId,
                 new DisplayCutout.ParcelableWrapper(displayCutout));
         mDragResizingChangeReported = true;
     }
diff --git a/services/core/java/com/android/server/wm/WindowStateAnimator.java b/services/core/java/com/android/server/wm/WindowStateAnimator.java
index 15ea5b5..e090cc5 100644
--- a/services/core/java/com/android/server/wm/WindowStateAnimator.java
+++ b/services/core/java/com/android/server/wm/WindowStateAnimator.java
@@ -1343,7 +1343,7 @@
         // is running.
         Trace.traceBegin(Trace.TRACE_TAG_WINDOW_MANAGER, "WSA#applyAnimationLocked");
         if (mWin.mToken.okToAnimate()) {
-            int anim = mPolicy.selectAnimationLw(mWin, transit);
+            int anim = mWin.getDisplayContent().getDisplayPolicy().selectAnimationLw(mWin, transit);
             int attr = -1;
             Animation a = null;
             if (anim != 0) {
diff --git a/services/tests/wmtests/src/com/android/server/policy/PhoneWindowManagerInsetsTest.java b/services/tests/servicestests/src/com/android/server/wm/DisplayPolicyInsetsTests.java
similarity index 71%
rename from services/tests/wmtests/src/com/android/server/policy/PhoneWindowManagerInsetsTest.java
rename to services/tests/servicestests/src/com/android/server/wm/DisplayPolicyInsetsTests.java
index f024fe7..18bd2e4 100644
--- a/services/tests/wmtests/src/com/android/server/policy/PhoneWindowManagerInsetsTest.java
+++ b/services/tests/servicestests/src/com/android/server/wm/DisplayPolicyInsetsTests.java
@@ -14,7 +14,7 @@
  * limitations under the License.
  */
 
-package com.android.server.policy;
+package com.android.server.wm;
 
 import static android.view.Surface.ROTATION_0;
 import static android.view.Surface.ROTATION_180;
@@ -25,36 +25,27 @@
 
 import android.graphics.Rect;
 import android.platform.test.annotations.Presubmit;
-import android.view.Display;
 import android.view.DisplayInfo;
 
 import androidx.test.filters.SmallTest;
+import androidx.test.runner.AndroidJUnit4;
 
-import org.junit.Before;
 import org.junit.Rule;
 import org.junit.Test;
 import org.junit.rules.ErrorCollector;
+import org.junit.runner.RunWith;
 
-/**
- * Build/Install/Run:
- *  atest WmTests:PhoneWindowManagerInsetsTest
- */
+@RunWith(AndroidJUnit4.class)
 @SmallTest
 @Presubmit
-public class PhoneWindowManagerInsetsTest extends PhoneWindowManagerTestBase {
+public class DisplayPolicyInsetsTests extends DisplayPolicyTestsBase {
 
     @Rule
     public final ErrorCollector mErrorCollector = new ErrorCollector();
 
-    @Before
-    public void setUp() throws Exception {
-        addStatusBar();
-        addNavigationBar();
-    }
-
     @Test
     public void portrait() {
-        DisplayInfo di = displayInfoForRotation(ROTATION_0, false /* withCutout */);
+        final DisplayInfo di = displayInfoForRotation(ROTATION_0, false /* withCutout */);
 
         verifyStableInsets(di, 0, STATUS_BAR_HEIGHT, 0, NAV_BAR_HEIGHT);
         verifyNonDecorInsets(di, 0, 0, 0, NAV_BAR_HEIGHT);
@@ -63,7 +54,7 @@
 
     @Test
     public void portrait_withCutout() {
-        DisplayInfo di = displayInfoForRotation(ROTATION_0, true /* withCutout */);
+        final DisplayInfo di = displayInfoForRotation(ROTATION_0, true /* withCutout */);
 
         verifyStableInsets(di, 0, STATUS_BAR_HEIGHT, 0, NAV_BAR_HEIGHT);
         verifyNonDecorInsets(di, 0, DISPLAY_CUTOUT_HEIGHT, 0, NAV_BAR_HEIGHT);
@@ -72,7 +63,7 @@
 
     @Test
     public void landscape() {
-        DisplayInfo di = displayInfoForRotation(ROTATION_90, false /* withCutout */);
+        final DisplayInfo di = displayInfoForRotation(ROTATION_90, false /* withCutout */);
 
         verifyStableInsets(di, 0, STATUS_BAR_HEIGHT, NAV_BAR_HEIGHT, 0);
         verifyNonDecorInsets(di, 0, 0, NAV_BAR_HEIGHT, 0);
@@ -81,7 +72,7 @@
 
     @Test
     public void landscape_withCutout() {
-        DisplayInfo di = displayInfoForRotation(ROTATION_90, true /* withCutout */);
+        final DisplayInfo di = displayInfoForRotation(ROTATION_90, true /* withCutout */);
 
         verifyStableInsets(di, DISPLAY_CUTOUT_HEIGHT, STATUS_BAR_HEIGHT, NAV_BAR_HEIGHT, 0);
         verifyNonDecorInsets(di, DISPLAY_CUTOUT_HEIGHT, 0, NAV_BAR_HEIGHT, 0);
@@ -90,7 +81,7 @@
 
     @Test
     public void seascape() {
-        DisplayInfo di = displayInfoForRotation(ROTATION_270, false /* withCutout */);
+        final DisplayInfo di = displayInfoForRotation(ROTATION_270, false /* withCutout */);
 
         verifyStableInsets(di, NAV_BAR_HEIGHT, STATUS_BAR_HEIGHT, 0, 0);
         verifyNonDecorInsets(di, NAV_BAR_HEIGHT, 0, 0, 0);
@@ -99,7 +90,7 @@
 
     @Test
     public void seascape_withCutout() {
-        DisplayInfo di = displayInfoForRotation(ROTATION_270, true /* withCutout */);
+        final DisplayInfo di = displayInfoForRotation(ROTATION_270, true /* withCutout */);
 
         verifyStableInsets(di, NAV_BAR_HEIGHT, STATUS_BAR_HEIGHT, DISPLAY_CUTOUT_HEIGHT, 0);
         verifyNonDecorInsets(di, NAV_BAR_HEIGHT, 0, DISPLAY_CUTOUT_HEIGHT, 0);
@@ -108,7 +99,7 @@
 
     @Test
     public void upsideDown() {
-        DisplayInfo di = displayInfoForRotation(ROTATION_180, false /* withCutout */);
+        final DisplayInfo di = displayInfoForRotation(ROTATION_180, false /* withCutout */);
 
         verifyStableInsets(di, 0, STATUS_BAR_HEIGHT, 0, NAV_BAR_HEIGHT);
         verifyNonDecorInsets(di, 0, 0, 0, NAV_BAR_HEIGHT);
@@ -117,7 +108,7 @@
 
     @Test
     public void upsideDown_withCutout() {
-        DisplayInfo di = displayInfoForRotation(ROTATION_180, true /* withCutout */);
+        final DisplayInfo di = displayInfoForRotation(ROTATION_180, true /* withCutout */);
 
         verifyStableInsets(di, 0, STATUS_BAR_HEIGHT, 0, NAV_BAR_HEIGHT + DISPLAY_CUTOUT_HEIGHT);
         verifyNonDecorInsets(di, 0, 0, 0, NAV_BAR_HEIGHT + DISPLAY_CUTOUT_HEIGHT);
@@ -151,35 +142,39 @@
 
     private Rect getStableInsetsLw(DisplayInfo di) {
         Rect result = new Rect();
-        mPolicy.getStableInsetsLw(di.rotation, di.logicalWidth, di.logicalHeight,
+        mDisplayPolicy.getStableInsetsLw(di.rotation, di.logicalWidth, di.logicalHeight,
                 di.displayCutout, result);
         return result;
     }
 
     private Rect getNonDecorInsetsLw(DisplayInfo di) {
         Rect result = new Rect();
-        mPolicy.getNonDecorInsetsLw(di.rotation, di.logicalWidth, di.logicalHeight,
+        mDisplayPolicy.getNonDecorInsetsLw(di.rotation, di.logicalWidth, di.logicalHeight,
                 di.displayCutout, result);
         return result;
     }
 
     private int getNonDecorDisplayWidth(DisplayInfo di) {
-        return mPolicy.getNonDecorDisplayWidth(di.logicalWidth, di.logicalHeight, di.rotation,
-                0 /* ui */, Display.DEFAULT_DISPLAY, di.displayCutout);
+        return mDisplayPolicy.getNonDecorDisplayWidth(di.logicalWidth, di.logicalHeight,
+                di.rotation, 0 /* ui */, di.displayCutout);
     }
 
     private int getNonDecorDisplayHeight(DisplayInfo di) {
-        return mPolicy.getNonDecorDisplayHeight(di.logicalWidth, di.logicalHeight, di.rotation,
-                0 /* ui */, Display.DEFAULT_DISPLAY, di.displayCutout);
+        return mDisplayPolicy.getNonDecorDisplayHeight(di.logicalWidth, di.logicalHeight,
+                di.rotation, 0 /* ui */, di.displayCutout);
     }
 
     private int getConfigDisplayWidth(DisplayInfo di) {
-        return mPolicy.getConfigDisplayWidth(di.logicalWidth, di.logicalHeight, di.rotation,
-                0 /* ui */, Display.DEFAULT_DISPLAY, di.displayCutout);
+        return mDisplayPolicy.getConfigDisplayWidth(di.logicalWidth, di.logicalHeight,
+                di.rotation, 0 /* ui */, di.displayCutout);
     }
 
     private int getConfigDisplayHeight(DisplayInfo di) {
-        return mPolicy.getConfigDisplayHeight(di.logicalWidth, di.logicalHeight, di.rotation,
-                0 /* ui */, Display.DEFAULT_DISPLAY, di.displayCutout);
+        return mDisplayPolicy.getConfigDisplayHeight(di.logicalWidth, di.logicalHeight,
+                di.rotation, 0 /* ui */, di.displayCutout);
+    }
+
+    private static DisplayInfo displayInfoForRotation(int rotation, boolean withDisplayCutout) {
+        return displayInfoAndCutoutForRotation(rotation, withDisplayCutout).first;
     }
 }
diff --git a/services/tests/servicestests/src/com/android/server/wm/DisplayPolicyLayoutTests.java b/services/tests/servicestests/src/com/android/server/wm/DisplayPolicyLayoutTests.java
new file mode 100644
index 0000000..a91c5e7
--- /dev/null
+++ b/services/tests/servicestests/src/com/android/server/wm/DisplayPolicyLayoutTests.java
@@ -0,0 +1,422 @@
+/*
+ * Copyright (C) 2018 The Android Open Source Project
+ *
+ * Licensed under the Apache License, Version 2.0 (the "License");
+ * you may not use this file except in compliance with the License.
+ * You may obtain a copy of the License at
+ *
+ *      http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS,
+ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ * See the License for the specific language governing permissions and
+ * limitations under the License.
+ */
+
+package com.android.server.wm;
+
+import static android.view.Surface.ROTATION_0;
+import static android.view.Surface.ROTATION_270;
+import static android.view.Surface.ROTATION_90;
+import static android.view.View.SYSTEM_UI_FLAG_FULLSCREEN;
+import static android.view.View.SYSTEM_UI_FLAG_LAYOUT_FULLSCREEN;
+import static android.view.ViewGroup.LayoutParams.MATCH_PARENT;
+import static android.view.WindowManager.LayoutParams.FLAG_DRAWS_SYSTEM_BAR_BACKGROUNDS;
+import static android.view.WindowManager.LayoutParams.FLAG_LAYOUT_INSET_DECOR;
+import static android.view.WindowManager.LayoutParams.FLAG_LAYOUT_IN_SCREEN;
+import static android.view.WindowManager.LayoutParams.LAYOUT_IN_DISPLAY_CUTOUT_MODE_ALWAYS;
+import static android.view.WindowManager.LayoutParams.LAYOUT_IN_DISPLAY_CUTOUT_MODE_NEVER;
+import static android.view.WindowManager.LayoutParams.PRIVATE_FLAG_FORCE_DRAW_STATUS_BAR_BACKGROUND;
+import static android.view.WindowManager.LayoutParams.TYPE_APPLICATION;
+import static android.view.WindowManager.LayoutParams.TYPE_APPLICATION_OVERLAY;
+
+import static org.hamcrest.Matchers.is;
+import static org.junit.Assert.assertEquals;
+import static org.junit.Assert.assertThat;
+import static org.mockito.Mockito.doNothing;
+import static org.mockito.Mockito.spy;
+
+import android.graphics.PixelFormat;
+import android.graphics.Rect;
+import android.platform.test.annotations.Presubmit;
+import android.util.Pair;
+import android.view.DisplayCutout;
+import android.view.DisplayInfo;
+import android.view.WindowManager;
+
+import androidx.test.filters.SmallTest;
+import androidx.test.runner.AndroidJUnit4;
+
+import com.android.server.wm.utils.WmDisplayCutout;
+
+import org.junit.Before;
+import org.junit.Test;
+import org.junit.runner.RunWith;
+
+@RunWith(AndroidJUnit4.class)
+@SmallTest
+@Presubmit
+public class DisplayPolicyLayoutTests extends DisplayPolicyTestsBase {
+
+    private DisplayFrames mFrames;
+    private WindowState mWindow;
+    private int mRotation = ROTATION_0;
+    private boolean mHasDisplayCutout;
+
+    @Before
+    public void setUp() throws Exception {
+        updateDisplayFrames();
+
+        mWindow = spy(createWindow(null, TYPE_APPLICATION, "window"));
+        // We only test window frames set by DisplayPolicy, so here prevents computeFrameLw from
+        // changing those frames.
+        doNothing().when(mWindow).computeFrameLw();
+
+        final WindowManager.LayoutParams attrs = mWindow.mAttrs;
+        attrs.width = MATCH_PARENT;
+        attrs.height = MATCH_PARENT;
+        attrs.flags =
+                FLAG_LAYOUT_IN_SCREEN | FLAG_LAYOUT_INSET_DECOR | FLAG_DRAWS_SYSTEM_BAR_BACKGROUNDS;
+        attrs.format = PixelFormat.TRANSLUCENT;
+    }
+
+    public void setRotation(int rotation) {
+        mRotation = rotation;
+        updateDisplayFrames();
+    }
+
+    public void addDisplayCutout() {
+        mHasDisplayCutout = true;
+        updateDisplayFrames();
+    }
+
+    private void updateDisplayFrames() {
+        final Pair<DisplayInfo, WmDisplayCutout> info = displayInfoAndCutoutForRotation(mRotation,
+                mHasDisplayCutout);
+        mFrames = new DisplayFrames(mDisplayContent.getDisplayId(), info.first, info.second);
+    }
+
+    @Test
+    public void layoutWindowLw_appDrawsBars() {
+        mWindow.mAttrs.flags |= FLAG_DRAWS_SYSTEM_BAR_BACKGROUNDS;
+        addWindow(mWindow);
+
+        mDisplayPolicy.beginLayoutLw(mFrames, 0 /* UI mode */);
+        mDisplayPolicy.layoutWindowLw(mWindow, null, mFrames);
+
+        assertInsetByTopBottom(mWindow.getParentFrame(), 0, 0);
+        assertInsetByTopBottom(mWindow.getStableFrameLw(), STATUS_BAR_HEIGHT, NAV_BAR_HEIGHT);
+        assertInsetByTopBottom(mWindow.getContentFrameLw(), STATUS_BAR_HEIGHT, NAV_BAR_HEIGHT);
+        assertInsetByTopBottom(mWindow.getDecorFrame(), 0, 0);
+        assertInsetBy(mWindow.getDisplayFrameLw(), 0, 0, 0, 0);
+    }
+
+    @Test
+    public void layoutWindowLw_appWontDrawBars() {
+        mWindow.mAttrs.flags &= ~FLAG_DRAWS_SYSTEM_BAR_BACKGROUNDS;
+        addWindow(mWindow);
+
+        mDisplayPolicy.beginLayoutLw(mFrames, 0 /* UI mode */);
+        mDisplayPolicy.layoutWindowLw(mWindow, null, mFrames);
+
+        assertInsetByTopBottom(mWindow.getParentFrame(), 0, NAV_BAR_HEIGHT);
+        assertInsetByTopBottom(mWindow.getStableFrameLw(), STATUS_BAR_HEIGHT, NAV_BAR_HEIGHT);
+        assertInsetByTopBottom(mWindow.getContentFrameLw(), STATUS_BAR_HEIGHT, NAV_BAR_HEIGHT);
+        assertInsetByTopBottom(mWindow.getDecorFrame(), STATUS_BAR_HEIGHT, NAV_BAR_HEIGHT);
+        assertInsetByTopBottom(mWindow.getDisplayFrameLw(), 0, NAV_BAR_HEIGHT);
+    }
+
+    @Test
+    public void layoutWindowLw_appWontDrawBars_forceStatus() throws Exception {
+        mWindow.mAttrs.flags &= ~FLAG_DRAWS_SYSTEM_BAR_BACKGROUNDS;
+        mWindow.mAttrs.privateFlags |= PRIVATE_FLAG_FORCE_DRAW_STATUS_BAR_BACKGROUND;
+        addWindow(mWindow);
+
+        mDisplayPolicy.beginLayoutLw(mFrames, 0 /* UI mode */);
+        mDisplayPolicy.layoutWindowLw(mWindow, null, mFrames);
+
+        assertInsetByTopBottom(mWindow.getParentFrame(), 0, NAV_BAR_HEIGHT);
+        assertInsetByTopBottom(mWindow.getStableFrameLw(), STATUS_BAR_HEIGHT, NAV_BAR_HEIGHT);
+        assertInsetByTopBottom(mWindow.getContentFrameLw(), STATUS_BAR_HEIGHT, NAV_BAR_HEIGHT);
+        assertInsetByTopBottom(mWindow.getDecorFrame(), 0, NAV_BAR_HEIGHT);
+        assertInsetByTopBottom(mWindow.getDisplayFrameLw(), 0, NAV_BAR_HEIGHT);
+    }
+
+    @Test
+    public void addingWindow_doesNotTamperWithSysuiFlags() {
+        mWindow.mAttrs.flags |= FLAG_DRAWS_SYSTEM_BAR_BACKGROUNDS;
+        addWindow(mWindow);
+
+        assertEquals(0, mWindow.mAttrs.systemUiVisibility);
+        assertEquals(0, mWindow.mAttrs.subtreeSystemUiVisibility);
+    }
+
+    @Test
+    public void layoutWindowLw_withDisplayCutout() {
+        addDisplayCutout();
+
+        addWindow(mWindow);
+
+        mDisplayPolicy.beginLayoutLw(mFrames, 0 /* UI mode */);
+        mDisplayPolicy.layoutWindowLw(mWindow, null, mFrames);
+
+        assertInsetByTopBottom(mWindow.getParentFrame(), 0, 0);
+        assertInsetByTopBottom(mWindow.getStableFrameLw(), STATUS_BAR_HEIGHT, NAV_BAR_HEIGHT);
+        assertInsetByTopBottom(mWindow.getContentFrameLw(), STATUS_BAR_HEIGHT, NAV_BAR_HEIGHT);
+        assertInsetByTopBottom(mWindow.getDecorFrame(), 0, 0);
+        assertInsetByTopBottom(mWindow.getDisplayFrameLw(), 0, 0);
+    }
+
+    @Test
+    public void layoutWindowLw_withDisplayCutout_never() {
+        addDisplayCutout();
+
+        mWindow.mAttrs.layoutInDisplayCutoutMode = LAYOUT_IN_DISPLAY_CUTOUT_MODE_NEVER;
+        addWindow(mWindow);
+
+        mDisplayPolicy.beginLayoutLw(mFrames, 0 /* UI mode */);
+        mDisplayPolicy.layoutWindowLw(mWindow, null, mFrames);
+
+        assertInsetByTopBottom(mWindow.getParentFrame(), STATUS_BAR_HEIGHT, 0);
+        assertInsetByTopBottom(mWindow.getStableFrameLw(), STATUS_BAR_HEIGHT, NAV_BAR_HEIGHT);
+        assertInsetByTopBottom(mWindow.getContentFrameLw(), STATUS_BAR_HEIGHT, NAV_BAR_HEIGHT);
+        assertInsetByTopBottom(mWindow.getDecorFrame(), 0, 0);
+        assertInsetByTopBottom(mWindow.getDisplayFrameLw(), STATUS_BAR_HEIGHT, 0);
+    }
+
+    @Test
+    public void layoutWindowLw_withDisplayCutout_layoutFullscreen() {
+        addDisplayCutout();
+
+        mWindow.mAttrs.subtreeSystemUiVisibility |= SYSTEM_UI_FLAG_LAYOUT_FULLSCREEN;
+        addWindow(mWindow);
+
+        mDisplayPolicy.beginLayoutLw(mFrames, 0 /* UI mode */);
+        mDisplayPolicy.layoutWindowLw(mWindow, null, mFrames);
+
+        assertInsetByTopBottom(mWindow.getParentFrame(), 0, 0);
+        assertInsetByTopBottom(mWindow.getStableFrameLw(), STATUS_BAR_HEIGHT, NAV_BAR_HEIGHT);
+        assertInsetByTopBottom(mWindow.getContentFrameLw(), STATUS_BAR_HEIGHT, NAV_BAR_HEIGHT);
+        assertInsetByTopBottom(mWindow.getDecorFrame(), 0, 0);
+        assertInsetBy(mWindow.getDisplayFrameLw(), 0, 0, 0, 0);
+    }
+
+    @Test
+    public void layoutWindowLw_withDisplayCutout_fullscreen() {
+        addDisplayCutout();
+
+        mWindow.mAttrs.subtreeSystemUiVisibility |= SYSTEM_UI_FLAG_FULLSCREEN;
+        addWindow(mWindow);
+
+        mDisplayPolicy.beginLayoutLw(mFrames, 0 /* UI mode */);
+        mDisplayPolicy.layoutWindowLw(mWindow, null, mFrames);
+
+        assertInsetByTopBottom(mWindow.getParentFrame(), STATUS_BAR_HEIGHT, 0);
+        assertInsetByTopBottom(mWindow.getStableFrameLw(), STATUS_BAR_HEIGHT, NAV_BAR_HEIGHT);
+        assertInsetByTopBottom(mWindow.getContentFrameLw(), STATUS_BAR_HEIGHT, NAV_BAR_HEIGHT);
+        assertInsetByTopBottom(mWindow.getDecorFrame(), 0, 0);
+        assertInsetByTopBottom(mWindow.getDisplayFrameLw(), STATUS_BAR_HEIGHT, 0);
+    }
+
+    @Test
+    public void layoutWindowLw_withDisplayCutout_fullscreenInCutout() {
+        addDisplayCutout();
+
+        mWindow.mAttrs.subtreeSystemUiVisibility |= SYSTEM_UI_FLAG_FULLSCREEN;
+        mWindow.mAttrs.layoutInDisplayCutoutMode = LAYOUT_IN_DISPLAY_CUTOUT_MODE_ALWAYS;
+        addWindow(mWindow);
+
+        mDisplayPolicy.beginLayoutLw(mFrames, 0 /* UI mode */);
+        mDisplayPolicy.layoutWindowLw(mWindow, null, mFrames);
+
+        assertInsetByTopBottom(mWindow.getParentFrame(), 0, 0);
+        assertInsetByTopBottom(mWindow.getStableFrameLw(), STATUS_BAR_HEIGHT, NAV_BAR_HEIGHT);
+        assertInsetByTopBottom(mWindow.getContentFrameLw(), STATUS_BAR_HEIGHT, NAV_BAR_HEIGHT);
+        assertInsetByTopBottom(mWindow.getDecorFrame(), 0, 0);
+        assertInsetByTopBottom(mWindow.getDisplayFrameLw(), 0, 0);
+    }
+
+
+    @Test
+    public void layoutWindowLw_withDisplayCutout_landscape() {
+        addDisplayCutout();
+        setRotation(ROTATION_90);
+        addWindow(mWindow);
+
+        mDisplayPolicy.beginLayoutLw(mFrames, 0 /* UI mode */);
+        mDisplayPolicy.layoutWindowLw(mWindow, null, mFrames);
+
+        assertInsetBy(mWindow.getParentFrame(), DISPLAY_CUTOUT_HEIGHT, 0, 0, 0);
+        assertInsetBy(mWindow.getStableFrameLw(), 0, STATUS_BAR_HEIGHT, NAV_BAR_HEIGHT, 0);
+        assertInsetBy(mWindow.getContentFrameLw(),
+                DISPLAY_CUTOUT_HEIGHT, STATUS_BAR_HEIGHT, NAV_BAR_HEIGHT, 0);
+        assertInsetBy(mWindow.getDecorFrame(), 0, 0, 0, 0);
+        assertInsetBy(mWindow.getDisplayFrameLw(), DISPLAY_CUTOUT_HEIGHT, 0, 0, 0);
+    }
+
+    @Test
+    public void layoutWindowLw_withDisplayCutout_seascape() {
+        addDisplayCutout();
+        setRotation(ROTATION_270);
+        addWindow(mWindow);
+
+        mDisplayPolicy.beginLayoutLw(mFrames, 0 /* UI mode */);
+        mDisplayPolicy.layoutWindowLw(mWindow, null, mFrames);
+
+        assertInsetBy(mWindow.getParentFrame(), 0, 0, DISPLAY_CUTOUT_HEIGHT, 0);
+        assertInsetBy(mWindow.getStableFrameLw(), NAV_BAR_HEIGHT, STATUS_BAR_HEIGHT, 0, 0);
+        assertInsetBy(mWindow.getContentFrameLw(),
+                NAV_BAR_HEIGHT, STATUS_BAR_HEIGHT, DISPLAY_CUTOUT_HEIGHT, 0);
+        assertInsetBy(mWindow.getDecorFrame(), 0, 0, 0, 0);
+        assertInsetBy(mWindow.getDisplayFrameLw(), 0, 0, DISPLAY_CUTOUT_HEIGHT, 0);
+    }
+
+    @Test
+    public void layoutWindowLw_withDisplayCutout_fullscreen_landscape() {
+        addDisplayCutout();
+        setRotation(ROTATION_90);
+
+        mWindow.mAttrs.subtreeSystemUiVisibility |= SYSTEM_UI_FLAG_LAYOUT_FULLSCREEN;
+        addWindow(mWindow);
+
+        mDisplayPolicy.beginLayoutLw(mFrames, 0 /* UI mode */);
+        mDisplayPolicy.layoutWindowLw(mWindow, null, mFrames);
+
+        assertInsetBy(mWindow.getParentFrame(), DISPLAY_CUTOUT_HEIGHT, 0, 0, 0);
+        assertInsetBy(mWindow.getStableFrameLw(), 0, STATUS_BAR_HEIGHT, NAV_BAR_HEIGHT, 0);
+        assertInsetBy(mWindow.getContentFrameLw(),
+                DISPLAY_CUTOUT_HEIGHT, STATUS_BAR_HEIGHT, NAV_BAR_HEIGHT, 0);
+        assertInsetBy(mWindow.getDecorFrame(), 0, 0, 0, 0);
+    }
+
+    @Test
+    public void layoutWindowLw_withDisplayCutout_floatingInScreen() {
+        addDisplayCutout();
+
+        mWindow.mAttrs.flags = FLAG_LAYOUT_IN_SCREEN;
+        mWindow.mAttrs.type = TYPE_APPLICATION_OVERLAY;
+        mWindow.mAttrs.width = DISPLAY_WIDTH;
+        mWindow.mAttrs.height = DISPLAY_HEIGHT;
+        addWindow(mWindow);
+
+        mDisplayPolicy.beginLayoutLw(mFrames, 0 /* UI mode */);
+        mDisplayPolicy.layoutWindowLw(mWindow, null, mFrames);
+
+        assertInsetByTopBottom(mWindow.getParentFrame(), 0, NAV_BAR_HEIGHT);
+        assertInsetByTopBottom(mWindow.getDisplayFrameLw(), STATUS_BAR_HEIGHT, NAV_BAR_HEIGHT);
+    }
+
+    @Test
+    public void layoutWindowLw_withDisplayCutout_fullscreenInCutout_landscape() {
+        addDisplayCutout();
+        setRotation(ROTATION_90);
+
+        mWindow.mAttrs.subtreeSystemUiVisibility |= SYSTEM_UI_FLAG_LAYOUT_FULLSCREEN;
+        mWindow.mAttrs.layoutInDisplayCutoutMode = LAYOUT_IN_DISPLAY_CUTOUT_MODE_ALWAYS;
+        addWindow(mWindow);
+
+        mDisplayPolicy.beginLayoutLw(mFrames, 0 /* UI mode */);
+        mDisplayPolicy.layoutWindowLw(mWindow, null, mFrames);
+
+        assertInsetBy(mWindow.getParentFrame(), 0, 0, 0, 0);
+        assertInsetBy(mWindow.getStableFrameLw(), 0, STATUS_BAR_HEIGHT, NAV_BAR_HEIGHT, 0);
+        assertInsetBy(mWindow.getContentFrameLw(),
+                DISPLAY_CUTOUT_HEIGHT, STATUS_BAR_HEIGHT, NAV_BAR_HEIGHT, 0);
+        assertInsetBy(mWindow.getDecorFrame(), 0, 0, 0, 0);
+    }
+
+    @Test
+    public void layoutHint_appWindow() {
+        // Initialize DisplayFrames
+        mDisplayPolicy.beginLayoutLw(mFrames, 0 /* UI mode */);
+
+        final Rect outFrame = new Rect();
+        final Rect outContentInsets = new Rect();
+        final Rect outStableInsets = new Rect();
+        final Rect outOutsets = new Rect();
+        final DisplayCutout.ParcelableWrapper outDisplayCutout =
+                new DisplayCutout.ParcelableWrapper();
+
+        mDisplayPolicy.getLayoutHintLw(mWindow.mAttrs, null, mFrames,
+                false /* floatingStack */, outFrame, outContentInsets, outStableInsets, outOutsets,
+                outDisplayCutout);
+
+        assertThat(outFrame, is(mFrames.mUnrestricted));
+        assertThat(outContentInsets, is(new Rect(0, STATUS_BAR_HEIGHT, 0, NAV_BAR_HEIGHT)));
+        assertThat(outStableInsets, is(new Rect(0, STATUS_BAR_HEIGHT, 0, NAV_BAR_HEIGHT)));
+        assertThat(outOutsets, is(new Rect()));
+        assertThat(outDisplayCutout, is(new DisplayCutout.ParcelableWrapper()));
+    }
+
+    @Test
+    public void layoutHint_appWindowInTask() {
+        // Initialize DisplayFrames
+        mDisplayPolicy.beginLayoutLw(mFrames, 0 /* UI mode */);
+
+        final Rect taskBounds = new Rect(100, 100, 200, 200);
+
+        final Rect outFrame = new Rect();
+        final Rect outContentInsets = new Rect();
+        final Rect outStableInsets = new Rect();
+        final Rect outOutsets = new Rect();
+        final DisplayCutout.ParcelableWrapper outDisplayCutout =
+                new DisplayCutout.ParcelableWrapper();
+
+        mDisplayPolicy.getLayoutHintLw(mWindow.mAttrs, taskBounds, mFrames,
+                false /* floatingStack */, outFrame, outContentInsets, outStableInsets, outOutsets,
+                outDisplayCutout);
+
+        assertThat(outFrame, is(taskBounds));
+        assertThat(outContentInsets, is(new Rect()));
+        assertThat(outStableInsets, is(new Rect()));
+        assertThat(outOutsets, is(new Rect()));
+        assertThat(outDisplayCutout, is(new DisplayCutout.ParcelableWrapper()));
+    }
+
+    @Test
+    public void layoutHint_appWindowInTask_outsideContentFrame() {
+        // Initialize DisplayFrames
+        mDisplayPolicy.beginLayoutLw(mFrames, 0 /* UI mode */);
+
+        // Task is in the nav bar area (usually does not happen, but this is similar enough to the
+        // possible overlap with the IME)
+        final Rect taskBounds = new Rect(100, mFrames.mContent.bottom + 1,
+                200, mFrames.mContent.bottom + 10);
+
+        final Rect outFrame = new Rect();
+        final Rect outContentInsets = new Rect();
+        final Rect outStableInsets = new Rect();
+        final Rect outOutsets = new Rect();
+        final DisplayCutout.ParcelableWrapper outDisplayCutout =
+                new DisplayCutout.ParcelableWrapper();
+
+        mDisplayPolicy.getLayoutHintLw(mWindow.mAttrs, taskBounds, mFrames,
+                true /* floatingStack */, outFrame, outContentInsets, outStableInsets, outOutsets,
+                outDisplayCutout);
+
+        assertThat(outFrame, is(taskBounds));
+        assertThat(outContentInsets, is(new Rect()));
+        assertThat(outStableInsets, is(new Rect()));
+        assertThat(outOutsets, is(new Rect()));
+        assertThat(outDisplayCutout, is(new DisplayCutout.ParcelableWrapper()));
+    }
+
+    /**
+     * Asserts that {@code actual} is inset by the given amounts from the full display rect.
+     *
+     * Convenience wrapper for when only the top and bottom inset are non-zero.
+     */
+    private void assertInsetByTopBottom(Rect actual, int expectedInsetTop,
+            int expectedInsetBottom) {
+        assertInsetBy(actual, 0, expectedInsetTop, 0, expectedInsetBottom);
+    }
+
+    /** Asserts that {@code actual} is inset by the given amounts from the full display rect. */
+    private void assertInsetBy(Rect actual, int expectedInsetLeft, int expectedInsetTop,
+            int expectedInsetRight, int expectedInsetBottom) {
+        assertEquals(new Rect(expectedInsetLeft, expectedInsetTop,
+                mFrames.mDisplayWidth - expectedInsetRight,
+                mFrames.mDisplayHeight - expectedInsetBottom), actual);
+    }
+}
diff --git a/services/tests/servicestests/src/com/android/server/wm/DisplayPolicyTests.java b/services/tests/servicestests/src/com/android/server/wm/DisplayPolicyTests.java
new file mode 100644
index 0000000..07d5fea
--- /dev/null
+++ b/services/tests/servicestests/src/com/android/server/wm/DisplayPolicyTests.java
@@ -0,0 +1,202 @@
+/*
+ * Copyright (C) 2018 The Android Open Source Project
+ *
+ * Licensed under the Apache License, Version 2.0 (the "License");
+ * you may not use this file except in compliance with the License.
+ * You may obtain a copy of the License at
+ *
+ *      http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS,
+ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ * See the License for the specific language governing permissions and
+ * limitations under the License.
+ */
+
+package com.android.server.wm;
+
+import static android.view.View.SYSTEM_UI_FLAG_LIGHT_NAVIGATION_BAR;
+import static android.view.ViewGroup.LayoutParams.MATCH_PARENT;
+import static android.view.ViewGroup.LayoutParams.WRAP_CONTENT;
+import static android.view.WindowManager.LayoutParams.FLAG_ALT_FOCUSABLE_IM;
+import static android.view.WindowManager.LayoutParams.FLAG_DIM_BEHIND;
+import static android.view.WindowManager.LayoutParams.FLAG_DRAWS_SYSTEM_BAR_BACKGROUNDS;
+import static android.view.WindowManager.LayoutParams.FLAG_LAYOUT_INSET_DECOR;
+import static android.view.WindowManager.LayoutParams.FLAG_LAYOUT_IN_SCREEN;
+import static android.view.WindowManager.LayoutParams.FLAG_NOT_FOCUSABLE;
+import static android.view.WindowManager.LayoutParams.TYPE_APPLICATION;
+import static android.view.WindowManager.LayoutParams.TYPE_BASE_APPLICATION;
+import static android.view.WindowManager.LayoutParams.TYPE_INPUT_METHOD;
+
+import static com.android.server.policy.WindowManagerPolicy.NAV_BAR_BOTTOM;
+import static com.android.server.policy.WindowManagerPolicy.NAV_BAR_RIGHT;
+
+import static org.junit.Assert.assertEquals;
+import static org.junit.Assert.assertNull;
+import static org.mockito.Mockito.spy;
+import static org.mockito.Mockito.when;
+
+import android.graphics.PixelFormat;
+import android.platform.test.annotations.Presubmit;
+import android.view.WindowManager;
+
+import androidx.test.filters.SmallTest;
+import androidx.test.runner.AndroidJUnit4;
+
+import org.junit.Test;
+import org.junit.runner.RunWith;
+
+@RunWith(AndroidJUnit4.class)
+@SmallTest
+@Presubmit
+public class DisplayPolicyTests extends WindowTestsBase {
+
+    private WindowState createOpaqueFullscreen(boolean hasLightNavBar) {
+        final WindowState win = createWindow(null, TYPE_BASE_APPLICATION, "opaqueFullscreen");
+        final WindowManager.LayoutParams attrs = win.mAttrs;
+        attrs.width = MATCH_PARENT;
+        attrs.height = MATCH_PARENT;
+        attrs.flags =
+                FLAG_LAYOUT_IN_SCREEN | FLAG_LAYOUT_INSET_DECOR | FLAG_DRAWS_SYSTEM_BAR_BACKGROUNDS;
+        attrs.format = PixelFormat.OPAQUE;
+        attrs.systemUiVisibility = attrs.subtreeSystemUiVisibility = win.mSystemUiVisibility =
+                hasLightNavBar ? SYSTEM_UI_FLAG_LIGHT_NAVIGATION_BAR : 0;
+        return win;
+    }
+
+    private WindowState createDimmingDialogWindow(boolean canBeImTarget) {
+        final WindowState win = spy(createWindow(null, TYPE_APPLICATION, "dimmingDialog"));
+        final WindowManager.LayoutParams attrs = win.mAttrs;
+        attrs.width = WRAP_CONTENT;
+        attrs.height = WRAP_CONTENT;
+        attrs.flags = FLAG_DIM_BEHIND | (canBeImTarget ? 0 : FLAG_ALT_FOCUSABLE_IM);
+        attrs.format = PixelFormat.TRANSLUCENT;
+        when(win.isDimming()).thenReturn(true);
+        return win;
+    }
+
+    private WindowState createInputMethodWindow(boolean visible, boolean drawNavBar,
+            boolean hasLightNavBar) {
+        final WindowState win = createWindow(null, TYPE_INPUT_METHOD, "inputMethod");
+        final WindowManager.LayoutParams attrs = win.mAttrs;
+        attrs.width = MATCH_PARENT;
+        attrs.height = MATCH_PARENT;
+        attrs.flags = FLAG_NOT_FOCUSABLE | FLAG_LAYOUT_IN_SCREEN
+                | (drawNavBar ? FLAG_DRAWS_SYSTEM_BAR_BACKGROUNDS : 0);
+        attrs.format = PixelFormat.TRANSPARENT;
+        attrs.systemUiVisibility = attrs.subtreeSystemUiVisibility = win.mSystemUiVisibility =
+                hasLightNavBar ? SYSTEM_UI_FLAG_LIGHT_NAVIGATION_BAR : 0;
+        win.mHasSurface = visible;
+        return win;
+    }
+
+    @Test
+    public void testChooseNavigationColorWindowLw() {
+        final WindowState opaque = createOpaqueFullscreen(false);
+
+        final WindowState dimmingImTarget = createDimmingDialogWindow(true);
+        final WindowState dimmingNonImTarget = createDimmingDialogWindow(false);
+
+        final WindowState visibleIme = createInputMethodWindow(true, true, false);
+        final WindowState invisibleIme = createInputMethodWindow(false, true, false);
+        final WindowState imeNonDrawNavBar = createInputMethodWindow(true, false, false);
+
+        // If everything is null, return null
+        assertNull(null, DisplayPolicy.chooseNavigationColorWindowLw(
+                null, null, null, NAV_BAR_BOTTOM));
+
+        assertEquals(opaque, DisplayPolicy.chooseNavigationColorWindowLw(
+                opaque, opaque, null, NAV_BAR_BOTTOM));
+        assertEquals(dimmingImTarget, DisplayPolicy.chooseNavigationColorWindowLw(
+                opaque, dimmingImTarget, null, NAV_BAR_BOTTOM));
+        assertEquals(dimmingNonImTarget, DisplayPolicy.chooseNavigationColorWindowLw(
+                opaque, dimmingNonImTarget, null, NAV_BAR_BOTTOM));
+
+        assertEquals(visibleIme, DisplayPolicy.chooseNavigationColorWindowLw(
+                null, null, visibleIme, NAV_BAR_BOTTOM));
+        assertEquals(visibleIme, DisplayPolicy.chooseNavigationColorWindowLw(
+                null, dimmingImTarget, visibleIme, NAV_BAR_BOTTOM));
+        assertEquals(dimmingNonImTarget, DisplayPolicy.chooseNavigationColorWindowLw(
+                null, dimmingNonImTarget, visibleIme, NAV_BAR_BOTTOM));
+        assertEquals(visibleIme, DisplayPolicy.chooseNavigationColorWindowLw(
+                opaque, opaque, visibleIme, NAV_BAR_BOTTOM));
+        assertEquals(visibleIme, DisplayPolicy.chooseNavigationColorWindowLw(
+                opaque, dimmingImTarget, visibleIme, NAV_BAR_BOTTOM));
+        assertEquals(dimmingNonImTarget, DisplayPolicy.chooseNavigationColorWindowLw(
+                opaque, dimmingNonImTarget, visibleIme, NAV_BAR_BOTTOM));
+
+        assertEquals(opaque, DisplayPolicy.chooseNavigationColorWindowLw(
+                opaque, opaque, invisibleIme, NAV_BAR_BOTTOM));
+        assertEquals(opaque, DisplayPolicy.chooseNavigationColorWindowLw(
+                opaque, opaque, invisibleIme, NAV_BAR_BOTTOM));
+        assertEquals(opaque, DisplayPolicy.chooseNavigationColorWindowLw(
+                opaque, opaque, visibleIme, NAV_BAR_RIGHT));
+
+        // Only IME windows that have FLAG_DRAWS_SYSTEM_BAR_BACKGROUNDS should be navigation color
+        // window.
+        assertEquals(opaque, DisplayPolicy.chooseNavigationColorWindowLw(
+                opaque, opaque, imeNonDrawNavBar, NAV_BAR_BOTTOM));
+        assertEquals(dimmingImTarget, DisplayPolicy.chooseNavigationColorWindowLw(
+                opaque, dimmingImTarget, imeNonDrawNavBar, NAV_BAR_BOTTOM));
+        assertEquals(dimmingNonImTarget, DisplayPolicy.chooseNavigationColorWindowLw(
+                opaque, dimmingNonImTarget, imeNonDrawNavBar, NAV_BAR_BOTTOM));
+    }
+
+    @Test
+    public void testUpdateLightNavigationBarLw() {
+        final WindowState opaqueDarkNavBar = createOpaqueFullscreen(false);
+        final WindowState opaqueLightNavBar = createOpaqueFullscreen(true);
+
+        final WindowState dimming = createDimmingDialogWindow(false);
+
+        final WindowState imeDrawDarkNavBar = createInputMethodWindow(true, true, false);
+        final WindowState imeDrawLightNavBar = createInputMethodWindow(true, true, true);
+
+        assertEquals(SYSTEM_UI_FLAG_LIGHT_NAVIGATION_BAR,
+                DisplayPolicy.updateLightNavigationBarLw(
+                        SYSTEM_UI_FLAG_LIGHT_NAVIGATION_BAR, null, null,
+                        null, null));
+
+        // Opaque top fullscreen window overrides SYSTEM_UI_FLAG_LIGHT_NAVIGATION_BAR flag.
+        assertEquals(0, DisplayPolicy.updateLightNavigationBarLw(
+                0, opaqueDarkNavBar, opaqueDarkNavBar, null, opaqueDarkNavBar));
+        assertEquals(0, DisplayPolicy.updateLightNavigationBarLw(
+                SYSTEM_UI_FLAG_LIGHT_NAVIGATION_BAR, opaqueDarkNavBar, opaqueDarkNavBar, null,
+                opaqueDarkNavBar));
+        assertEquals(SYSTEM_UI_FLAG_LIGHT_NAVIGATION_BAR,
+                DisplayPolicy.updateLightNavigationBarLw(0, opaqueLightNavBar,
+                        opaqueLightNavBar, null, opaqueLightNavBar));
+        assertEquals(SYSTEM_UI_FLAG_LIGHT_NAVIGATION_BAR,
+                DisplayPolicy.updateLightNavigationBarLw(SYSTEM_UI_FLAG_LIGHT_NAVIGATION_BAR,
+                        opaqueLightNavBar, opaqueLightNavBar, null, opaqueLightNavBar));
+
+        // Dimming window clears SYSTEM_UI_FLAG_LIGHT_NAVIGATION_BAR.
+        assertEquals(0, DisplayPolicy.updateLightNavigationBarLw(
+                0, opaqueDarkNavBar, dimming, null, dimming));
+        assertEquals(0, DisplayPolicy.updateLightNavigationBarLw(
+                0, opaqueLightNavBar, dimming, null, dimming));
+        assertEquals(0, DisplayPolicy.updateLightNavigationBarLw(
+                SYSTEM_UI_FLAG_LIGHT_NAVIGATION_BAR, opaqueDarkNavBar, dimming, null, dimming));
+        assertEquals(0, DisplayPolicy.updateLightNavigationBarLw(
+                SYSTEM_UI_FLAG_LIGHT_NAVIGATION_BAR, opaqueLightNavBar, dimming, null, dimming));
+        assertEquals(0, DisplayPolicy.updateLightNavigationBarLw(
+                SYSTEM_UI_FLAG_LIGHT_NAVIGATION_BAR, opaqueLightNavBar, dimming, imeDrawLightNavBar,
+                dimming));
+
+        // IME window clears SYSTEM_UI_FLAG_LIGHT_NAVIGATION_BAR
+        assertEquals(0, DisplayPolicy.updateLightNavigationBarLw(
+                SYSTEM_UI_FLAG_LIGHT_NAVIGATION_BAR, null, null, imeDrawDarkNavBar,
+                imeDrawDarkNavBar));
+
+        // Even if the top fullscreen has SYSTEM_UI_FLAG_LIGHT_NAVIGATION_BAR, IME window wins.
+        assertEquals(0, DisplayPolicy.updateLightNavigationBarLw(
+                SYSTEM_UI_FLAG_LIGHT_NAVIGATION_BAR, opaqueLightNavBar, opaqueLightNavBar,
+                imeDrawDarkNavBar, imeDrawDarkNavBar));
+
+        // IME window should be able to use SYSTEM_UI_FLAG_LIGHT_NAVIGATION_BAR.
+        assertEquals(SYSTEM_UI_FLAG_LIGHT_NAVIGATION_BAR,
+                DisplayPolicy.updateLightNavigationBarLw(0, opaqueDarkNavBar,
+                        opaqueDarkNavBar, imeDrawLightNavBar, imeDrawLightNavBar));
+    }
+}
diff --git a/services/tests/servicestests/src/com/android/server/wm/DisplayPolicyTestsBase.java b/services/tests/servicestests/src/com/android/server/wm/DisplayPolicyTestsBase.java
new file mode 100644
index 0000000..1d63c57
--- /dev/null
+++ b/services/tests/servicestests/src/com/android/server/wm/DisplayPolicyTestsBase.java
@@ -0,0 +1,184 @@
+/*
+ * Copyright (C) 2018 The Android Open Source Project
+ *
+ * Licensed under the Apache License, Version 2.0 (the "License");
+ * you may not use this file except in compliance with the License.
+ * You may obtain a copy of the License at
+ *
+ *      http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS,
+ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ * See the License for the specific language governing permissions and
+ * limitations under the License.
+ */
+
+package com.android.server.wm;
+
+import static android.util.DisplayMetrics.DENSITY_DEFAULT;
+import static android.view.DisplayCutout.BOUNDS_POSITION_BOTTOM;
+import static android.view.DisplayCutout.BOUNDS_POSITION_LEFT;
+import static android.view.DisplayCutout.BOUNDS_POSITION_RIGHT;
+import static android.view.DisplayCutout.BOUNDS_POSITION_TOP;
+import static android.view.Surface.ROTATION_0;
+import static android.view.Surface.ROTATION_180;
+import static android.view.Surface.ROTATION_270;
+import static android.view.Surface.ROTATION_90;
+
+import static com.android.server.wm.utils.CoordinateTransforms.transformPhysicalToLogicalCoordinates;
+
+import static org.junit.Assert.assertEquals;
+import static org.mockito.Mockito.spy;
+import static org.mockito.Mockito.when;
+
+import android.content.Context;
+import android.content.ContextWrapper;
+import android.content.pm.PackageManager;
+import android.content.res.Resources;
+import android.graphics.Matrix;
+import android.graphics.RectF;
+import android.os.IBinder;
+import android.testing.TestableResources;
+import android.util.Pair;
+import android.view.DisplayCutout;
+import android.view.DisplayInfo;
+import android.view.Gravity;
+import android.view.View;
+import android.view.WindowManagerGlobal;
+
+import com.android.internal.R;
+import com.android.server.wm.utils.WmDisplayCutout;
+
+import org.junit.Before;
+
+public class DisplayPolicyTestsBase extends WindowTestsBase {
+
+    static final int DISPLAY_WIDTH = 500;
+    static final int DISPLAY_HEIGHT = 1000;
+    static final int DISPLAY_DENSITY = 320;
+
+    static final int STATUS_BAR_HEIGHT = 10;
+    static final int NAV_BAR_HEIGHT = 15;
+    static final int DISPLAY_CUTOUT_HEIGHT = 8;
+
+    DisplayPolicy mDisplayPolicy;
+
+    @Before
+    public void setUpBase() {
+        super.setUpBase();
+        mDisplayPolicy = spy(mDisplayContent.getDisplayPolicy());
+
+        final TestContextWrapper context =
+                new TestContextWrapper(mDisplayPolicy.getSystemUiContext());
+        final TestableResources resources = context.getResourceMocker();
+        resources.addOverride(R.dimen.status_bar_height_portrait, STATUS_BAR_HEIGHT);
+        resources.addOverride(R.dimen.status_bar_height_landscape, STATUS_BAR_HEIGHT);
+        resources.addOverride(R.dimen.navigation_bar_height, NAV_BAR_HEIGHT);
+        resources.addOverride(R.dimen.navigation_bar_height_landscape, NAV_BAR_HEIGHT);
+        resources.addOverride(R.dimen.navigation_bar_width, NAV_BAR_HEIGHT);
+        when(mDisplayPolicy.getSystemUiContext()).thenReturn(context);
+        when(mDisplayPolicy.hasNavigationBar()).thenReturn(true);
+
+        final int shortSizeDp =
+                Math.min(DISPLAY_WIDTH, DISPLAY_HEIGHT) * DENSITY_DEFAULT / DISPLAY_DENSITY;
+        final int longSizeDp =
+                Math.min(DISPLAY_WIDTH, DISPLAY_HEIGHT) * DENSITY_DEFAULT / DISPLAY_DENSITY;
+        mDisplayContent.getDisplayRotation().configure(
+                DISPLAY_WIDTH, DISPLAY_HEIGHT, shortSizeDp, longSizeDp);
+        mDisplayPolicy.configure(DISPLAY_WIDTH, DISPLAY_HEIGHT, shortSizeDp);
+        mDisplayPolicy.onConfigurationChanged();
+
+        mStatusBarWindow.mAttrs.gravity = Gravity.TOP;
+        addWindow(mStatusBarWindow);
+        mDisplayPolicy.mLastSystemUiFlags |= View.STATUS_BAR_TRANSPARENT;
+
+        mNavBarWindow.mAttrs.gravity = Gravity.BOTTOM;
+        addWindow(mNavBarWindow);
+        mDisplayPolicy.mLastSystemUiFlags |= View.NAVIGATION_BAR_TRANSPARENT;
+    }
+
+    void addWindow(WindowState win) {
+        mDisplayPolicy.adjustWindowParamsLw(win, win.mAttrs, true /* hasStatusBarPermission */);
+        assertEquals(WindowManagerGlobal.ADD_OKAY,
+                mDisplayPolicy.prepareAddWindowLw(win, win.mAttrs));
+        win.mHasSurface = true;
+    }
+
+    static Pair<DisplayInfo, WmDisplayCutout> displayInfoAndCutoutForRotation(int rotation,
+            boolean withDisplayCutout) {
+        final DisplayInfo info = new DisplayInfo();
+        WmDisplayCutout cutout = null;
+
+        final boolean flippedDimensions = rotation == ROTATION_90 || rotation == ROTATION_270;
+        info.logicalWidth = flippedDimensions ? DISPLAY_HEIGHT : DISPLAY_WIDTH;
+        info.logicalHeight = flippedDimensions ? DISPLAY_WIDTH : DISPLAY_HEIGHT;
+        info.rotation = rotation;
+        if (withDisplayCutout) {
+            cutout = WmDisplayCutout.computeSafeInsets(
+                    displayCutoutForRotation(rotation), info.logicalWidth,
+                    info.logicalHeight);
+            info.displayCutout = cutout.getDisplayCutout();
+        } else {
+            info.displayCutout = null;
+        }
+        return Pair.create(info, cutout);
+    }
+
+    private static DisplayCutout displayCutoutForRotation(int rotation) {
+        final RectF rectF =
+                new RectF(DISPLAY_WIDTH / 4, 0, DISPLAY_WIDTH * 3 / 4, DISPLAY_CUTOUT_HEIGHT);
+
+        final Matrix m = new Matrix();
+        transformPhysicalToLogicalCoordinates(rotation, DISPLAY_WIDTH, DISPLAY_HEIGHT, m);
+        m.mapRect(rectF);
+
+        int pos = -1;
+        switch (rotation) {
+            case ROTATION_0:
+                pos = BOUNDS_POSITION_TOP;
+                break;
+            case ROTATION_90:
+                pos = BOUNDS_POSITION_LEFT;
+                break;
+            case ROTATION_180:
+                pos = BOUNDS_POSITION_BOTTOM;
+                break;
+            case ROTATION_270:
+                pos = BOUNDS_POSITION_RIGHT;
+                break;
+        }
+
+        return DisplayCutout.fromBoundingRect((int) rectF.left, (int) rectF.top,
+                (int) rectF.right, (int) rectF.bottom, pos);
+    }
+
+    static class TestContextWrapper extends ContextWrapper {
+        private final TestableResources mResourceMocker;
+
+        TestContextWrapper(Context targetContext) {
+            super(targetContext);
+            mResourceMocker = new TestableResources(targetContext.getResources());
+        }
+
+        @Override
+        public int checkPermission(String permission, int pid, int uid) {
+            return PackageManager.PERMISSION_GRANTED;
+        }
+
+        @Override
+        public int checkPermission(String permission, int pid, int uid, IBinder callerToken) {
+            return PackageManager.PERMISSION_GRANTED;
+        }
+
+        @Override
+        public Resources getResources() {
+            return mResourceMocker.getResources();
+        }
+
+        TestableResources getResourceMocker() {
+            return mResourceMocker;
+        }
+    }
+
+}
diff --git a/services/tests/servicestests/src/com/android/server/wm/DockedStackDividerControllerTests.java b/services/tests/servicestests/src/com/android/server/wm/DockedStackDividerControllerTests.java
new file mode 100644
index 0000000..a04bf16
--- /dev/null
+++ b/services/tests/servicestests/src/com/android/server/wm/DockedStackDividerControllerTests.java
@@ -0,0 +1,91 @@
+/*
+ * Copyright (C) 2018 The Android Open Source Project
+ *
+ * Licensed under the Apache License, Version 2.0 (the "License");
+ * you may not use this file except in compliance with the License.
+ * You may obtain a copy of the License at
+ *
+ *      http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS,
+ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ * See the License for the specific language governing permissions and
+ * limitations under the License.
+ */
+
+package com.android.server.wm;
+
+import static android.view.WindowManager.DOCKED_BOTTOM;
+import static android.view.WindowManager.DOCKED_LEFT;
+import static android.view.WindowManager.DOCKED_RIGHT;
+import static android.view.WindowManager.DOCKED_TOP;
+import static android.view.WindowManagerPolicyConstants.NAV_BAR_BOTTOM;
+import static android.view.WindowManagerPolicyConstants.NAV_BAR_LEFT;
+import static android.view.WindowManagerPolicyConstants.NAV_BAR_RIGHT;
+
+import static org.junit.Assert.assertFalse;
+import static org.junit.Assert.assertTrue;
+
+import android.platform.test.annotations.Presubmit;
+
+import androidx.test.filters.SmallTest;
+import androidx.test.runner.AndroidJUnit4;
+
+import org.junit.Test;
+import org.junit.runner.RunWith;
+
+@RunWith(AndroidJUnit4.class)
+@SmallTest
+@Presubmit
+public class DockedStackDividerControllerTests {
+
+    @Test
+    public void testIsDockSideAllowedDockTop() {
+        // Docked top is always allowed
+        assertTrue(DockedStackDividerController.isDockSideAllowed(DOCKED_TOP, DOCKED_LEFT,
+                NAV_BAR_BOTTOM, true /* navigationBarCanMove */));
+        assertTrue(DockedStackDividerController.isDockSideAllowed(DOCKED_TOP, DOCKED_LEFT,
+                NAV_BAR_BOTTOM, false /* navigationBarCanMove */));
+    }
+
+    @Test
+    public void testIsDockSideAllowedDockBottom() {
+        // Cannot dock bottom
+        assertFalse(DockedStackDividerController.isDockSideAllowed(DOCKED_BOTTOM, DOCKED_LEFT,
+                NAV_BAR_BOTTOM, true /* navigationBarCanMove */));
+    }
+
+    @Test
+    public void testIsDockSideAllowedNavigationBarMovable() {
+        assertFalse(DockedStackDividerController.isDockSideAllowed(DOCKED_LEFT, DOCKED_LEFT,
+                NAV_BAR_BOTTOM, true /* navigationBarCanMove */));
+        assertFalse(DockedStackDividerController.isDockSideAllowed(DOCKED_LEFT, DOCKED_LEFT,
+                NAV_BAR_LEFT, true /* navigationBarCanMove */));
+        assertTrue(DockedStackDividerController.isDockSideAllowed(DOCKED_LEFT, DOCKED_LEFT,
+                NAV_BAR_RIGHT, true /* navigationBarCanMove */));
+        assertFalse(DockedStackDividerController.isDockSideAllowed(DOCKED_RIGHT, DOCKED_LEFT,
+                NAV_BAR_BOTTOM, true /* navigationBarCanMove */));
+        assertFalse(DockedStackDividerController.isDockSideAllowed(DOCKED_RIGHT, DOCKED_LEFT,
+                NAV_BAR_RIGHT, true /* navigationBarCanMove */));
+        assertTrue(DockedStackDividerController.isDockSideAllowed(DOCKED_RIGHT, DOCKED_LEFT,
+                NAV_BAR_LEFT, true /* navigationBarCanMove */));
+    }
+
+    @Test
+    public void testIsDockSideAllowedNavigationBarNotMovable() {
+        // Navigation bar is not movable such as tablets
+        assertTrue(DockedStackDividerController.isDockSideAllowed(DOCKED_LEFT, DOCKED_LEFT,
+                NAV_BAR_BOTTOM, false /* navigationBarCanMove */));
+        assertTrue(DockedStackDividerController.isDockSideAllowed(DOCKED_LEFT, DOCKED_TOP,
+                NAV_BAR_BOTTOM, false /* navigationBarCanMove */));
+        assertFalse(DockedStackDividerController.isDockSideAllowed(DOCKED_LEFT, DOCKED_RIGHT,
+                NAV_BAR_BOTTOM, false /* navigationBarCanMove */));
+        assertFalse(DockedStackDividerController.isDockSideAllowed(DOCKED_RIGHT, DOCKED_LEFT,
+                NAV_BAR_BOTTOM, false /* navigationBarCanMove */));
+        assertFalse(DockedStackDividerController.isDockSideAllowed(DOCKED_RIGHT, DOCKED_TOP,
+                NAV_BAR_BOTTOM, false /* navigationBarCanMove */));
+        assertTrue(DockedStackDividerController.isDockSideAllowed(DOCKED_RIGHT, DOCKED_RIGHT,
+                NAV_BAR_BOTTOM, false /* navigationBarCanMove */));
+    }
+}
diff --git a/services/tests/servicestests/src/com/android/server/wm/RecentsAnimationControllerTest.java b/services/tests/servicestests/src/com/android/server/wm/RecentsAnimationControllerTest.java
index fe5fc06..ee3bba7 100644
--- a/services/tests/servicestests/src/com/android/server/wm/RecentsAnimationControllerTest.java
+++ b/services/tests/servicestests/src/com/android/server/wm/RecentsAnimationControllerTest.java
@@ -123,6 +123,8 @@
         final AppWindowToken hiddenAppWindow = createAppWindowToken(mDisplayContent,
                 WINDOWING_MODE_FULLSCREEN, ACTIVITY_TYPE_STANDARD);
         hiddenAppWindow.setHidden(true);
+        mDisplayContent.getConfiguration().windowConfiguration.setRotation(
+                mDisplayContent.getRotation());
         mController.initialize(mDisplayContent, ACTIVITY_TYPE_HOME, new SparseBooleanArray());
 
         // Ensure that we are animating the target activity as well
diff --git a/services/tests/servicestests/src/com/android/server/wm/TestWindowManagerPolicy.java b/services/tests/servicestests/src/com/android/server/wm/TestWindowManagerPolicy.java
index 0165e7d..7b542cb 100644
--- a/services/tests/servicestests/src/com/android/server/wm/TestWindowManagerPolicy.java
+++ b/services/tests/servicestests/src/com/android/server/wm/TestWindowManagerPolicy.java
@@ -26,12 +26,10 @@
 import android.content.Context;
 import android.content.res.CompatibilityInfo;
 import android.content.res.Configuration;
-import android.graphics.Rect;
 import android.os.Bundle;
 import android.os.IBinder;
 import android.os.RemoteException;
 import android.util.proto.ProtoOutputStream;
-import android.view.DisplayCutout;
 import android.view.IWindow;
 import android.view.IWindowManager;
 import android.view.KeyEvent;
@@ -48,7 +46,6 @@
 class TestWindowManagerPolicy implements WindowManagerPolicy {
     private final Supplier<WindowManagerService> mWmSupplier;
 
-    int rotationToReport = 0;
     boolean keyguardShowingAndNotOccluded = false;
 
     private Runnable mRunnableWhenAddingSplashScreen;
@@ -81,11 +78,6 @@
     }
 
     @Override
-    public void adjustWindowParamsLw(WindowState win, WindowManager.LayoutParams attrs,
-            boolean hasStatusBarServicePermission) {
-    }
-
-    @Override
     public void adjustConfigurationLw(Configuration config, int keyboardPresence,
             int navigationPresence) {
     }
@@ -96,30 +88,6 @@
     }
 
     @Override
-    public int getNonDecorDisplayWidth(int fullWidth, int fullHeight, int rotation, int uiMode,
-            int displayId, DisplayCutout displayCutout) {
-        return 0;
-    }
-
-    @Override
-    public int getNonDecorDisplayHeight(int fullWidth, int fullHeight, int rotation, int uiMode,
-            int displayId, DisplayCutout displayCutout) {
-        return 0;
-    }
-
-    @Override
-    public int getConfigDisplayWidth(int fullWidth, int fullHeight, int rotation, int uiMode,
-            int displayId, DisplayCutout displayCutout) {
-        return 0;
-    }
-
-    @Override
-    public int getConfigDisplayHeight(int fullWidth, int fullHeight, int rotation, int uiMode,
-            int displayId, DisplayCutout displayCutout) {
-        return 0;
-    }
-
-    @Override
     public boolean isKeyguardHostWindow(WindowManager.LayoutParams attrs) {
         return attrs.type == TYPE_STATUS_BAR;
     }
@@ -166,28 +134,7 @@
     }
 
     @Override
-    public int prepareAddWindowLw(WindowState win,
-            WindowManager.LayoutParams attrs) {
-        return 0;
-    }
-
-    @Override
-    public void removeWindowLw(WindowState win) {
-    }
-
-    @Override
-    public int selectAnimationLw(WindowState win, int transit) {
-        return 0;
-    }
-
-    @Override
-    public void selectRotationAnimationLw(int[] anim) {
-    }
-
-    @Override
-    public boolean validateRotationAnimationLw(int exitAnimId, int enterAnimId,
-            boolean forceDefault) {
-        return false;
+    public void setKeyguardCandidateLw(WindowState win) {
     }
 
     @Override
@@ -222,32 +169,11 @@
     }
 
     @Override
-    public int getSystemDecorLayerLw() {
-        return 0;
+    public void applyKeyguardPolicyLw(WindowState win, WindowState imeTarget) {
     }
 
     @Override
-    public void beginPostLayoutPolicyLw(int displayWidth, int displayHeight) {
-    }
-
-    @Override
-    public void applyPostLayoutPolicyLw(WindowState win, WindowManager.LayoutParams attrs,
-            WindowState attached, WindowState imeTarget) {
-    }
-
-    @Override
-    public int finishPostLayoutPolicyLw() {
-        return 0;
-    }
-
-    @Override
-    public boolean allowAppAnimationsLw() {
-        return false;
-    }
-
-    @Override
-    public int focusChangedLw(WindowState lastFocus, WindowState newFocus) {
-        return 0;
+    public void setAllowLockscreenWhenOn(int displayId, boolean allow) {
     }
 
     @Override
@@ -349,11 +275,6 @@
     }
 
     @Override
-    public boolean isShowingDreamLw() {
-        return false;
-    }
-
-    @Override
     public void onKeyguardOccludedChangedLw(boolean occluded) {
     }
 
@@ -399,11 +320,6 @@
     }
 
     @Override
-    public int adjustSystemUiVisibilityLw(int visibility) {
-        return 0;
-    }
-
-    @Override
     public boolean hasNavigationBar() {
         return false;
     }
@@ -421,6 +337,16 @@
     }
 
     @Override
+    public boolean isUserSetupComplete() {
+        return false;
+    }
+
+    @Override
+    public int getUiMode() {
+        return 0;
+    }
+
+    @Override
     public void setCurrentUserLw(int newUserId) {
     }
 
@@ -446,43 +372,6 @@
     }
 
     @Override
-    public void getStableInsetsLw(int displayRotation, int displayWidth, int displayHeight,
-            DisplayCutout cutout, Rect outInsets) {
-    }
-
-    @Override
-    public boolean isNavBarForcedShownLw(WindowState win) {
-        return false;
-    }
-
-    @NavigationBarPosition
-    @Override
-    public int getNavBarPosition() {
-        return NAV_BAR_BOTTOM;
-    }
-
-    @Override
-    public void getNonDecorInsetsLw(int displayRotation, int displayWidth, int displayHeight,
-            DisplayCutout cutout, Rect outInsets) {
-    }
-
-    @Override
-    public boolean isDockSideAllowed(int dockSide, int originalDockSide, int displayWidth,
-            int displayHeight, int displayRotation) {
-        return false;
-    }
-
-    @Override
-    public void onConfigurationChanged(DisplayContentInfo displayContentInfo) {
-    }
-
-    @Override
-    public boolean shouldRotateSeamlessly(DisplayRotation displayRotation, int oldRotation,
-            int newRotation) {
-        return false;
-    }
-
-    @Override
     public void setPipVisibilityLw(boolean visible) {
     }
 
@@ -508,10 +397,6 @@
     }
 
     @Override
-    public void onLockTaskStateChangedLw(int lockTaskState) {
-    }
-
-    @Override
     public boolean setAodShowing(boolean aodShowing) {
         return false;
     }
diff --git a/services/tests/servicestests/src/com/android/server/wm/WindowFrameTests.java b/services/tests/servicestests/src/com/android/server/wm/WindowFrameTests.java
index b0c8d8b..227eb00 100644
--- a/services/tests/servicestests/src/com/android/server/wm/WindowFrameTests.java
+++ b/services/tests/servicestests/src/com/android/server/wm/WindowFrameTests.java
@@ -113,9 +113,6 @@
 
     @Before
     public void setUp() throws Exception {
-        // Just any non zero value.
-        mWm.mSystemDecorLayer = 10000;
-
         mWindowToken = WindowTestUtils.createTestAppWindowToken(
                 mWm.getDefaultDisplayContentLocked());
         mStubStack = new TaskStack(mWm, 0, null);
diff --git a/services/tests/servicestests/src/com/android/server/wm/WindowTestUtils.java b/services/tests/servicestests/src/com/android/server/wm/WindowTestUtils.java
index d6fea09..60c0459 100644
--- a/services/tests/servicestests/src/com/android/server/wm/WindowTestUtils.java
+++ b/services/tests/servicestests/src/com/android/server/wm/WindowTestUtils.java
@@ -28,19 +28,15 @@
 import static org.mockito.Mockito.anyInt;
 import static org.mockito.Mockito.doAnswer;
 import static org.mockito.Mockito.mock;
-import static org.mockito.Mockito.when;
 
 import android.app.ActivityManager;
 import android.content.ComponentName;
-import android.content.Context;
 import android.content.res.Configuration;
 import android.graphics.Rect;
 import android.os.Binder;
 import android.os.IBinder;
-import android.view.Display;
 import android.view.IApplicationToken;
 import android.view.IWindow;
-import android.view.Surface;
 import android.view.SurfaceControl.Transaction;
 import android.view.WindowManager;
 
@@ -53,37 +49,6 @@
 public class WindowTestUtils {
     private static int sNextTaskId = 0;
 
-    /** An extension of {@link DisplayContent} to gain package scoped access. */
-    public static class TestDisplayContent extends DisplayContent {
-
-        private TestDisplayContent(Display display, WindowManagerService service,
-                DisplayWindowController controller) {
-            super(display, service, controller);
-        }
-
-        /** Create a mocked default {@link DisplayContent}. */
-        public static TestDisplayContent create(Context context) {
-            final TestDisplayContent displayContent = mock(TestDisplayContent.class);
-            displayContent.isDefaultDisplay = true;
-
-            final DisplayPolicy displayPolicy = mock(DisplayPolicy.class);
-            when(displayPolicy.navigationBarCanMove()).thenReturn(true);
-            when(displayPolicy.hasNavigationBar()).thenReturn(true);
-
-            final DisplayRotation displayRotation = new DisplayRotation(
-                    mock(WindowManagerService.class), displayContent, displayPolicy,
-                    context, new Object());
-            displayRotation.mPortraitRotation = Surface.ROTATION_0;
-            displayRotation.mLandscapeRotation = Surface.ROTATION_90;
-            displayRotation.mUpsideDownRotation = Surface.ROTATION_180;
-            displayRotation.mSeascapeRotation = Surface.ROTATION_270;
-
-            when(displayContent.getDisplayRotation()).thenReturn(displayRotation);
-
-            return displayContent;
-        }
-    }
-
     /**
      * Creates a mock instance of {@link StackWindowController}.
      */
diff --git a/services/tests/wmtests/src/com/android/server/policy/FakeWindowState.java b/services/tests/wmtests/src/com/android/server/policy/FakeWindowState.java
deleted file mode 100644
index d4f2b06..0000000
--- a/services/tests/wmtests/src/com/android/server/policy/FakeWindowState.java
+++ /dev/null
@@ -1,260 +0,0 @@
-/*
- * Copyright (C) 2017 The Android Open Source Project
- *
- * Licensed under the Apache License, Version 2.0 (the "License");
- * you may not use this file except in compliance with the License.
- * You may obtain a copy of the License at
- *
- *      http://www.apache.org/licenses/LICENSE-2.0
- *
- * Unless required by applicable law or agreed to in writing, software
- * distributed under the License is distributed on an "AS IS" BASIS,
- * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
- * See the License for the specific language governing permissions and
- * limitations under the License.
- */
-
-package com.android.server.policy;
-
-import android.graphics.Rect;
-import android.util.proto.ProtoOutputStream;
-import android.view.Display;
-import android.view.IApplicationToken;
-import android.view.WindowManager;
-
-import com.android.server.wm.WindowFrames;
-
-public class FakeWindowState implements WindowManagerPolicy.WindowState {
-
-    private WindowFrames mWindowFrames = new WindowFrames();
-
-    public WindowManager.LayoutParams attrs;
-    public int displayId;
-    public boolean isVoiceInteraction;
-    public boolean inMultiWindowMode;
-    public boolean visible = true;
-    public int surfaceLayer = 1;
-    public boolean isDimming = false;
-
-    public boolean policyVisible = true;
-
-    @Override
-    public int getOwningUid() {
-        throw new UnsupportedOperationException("not implemented");
-    }
-
-    @Override
-    public String getOwningPackage() {
-        throw new UnsupportedOperationException("not implemented");
-    }
-
-    @Override
-    public void computeFrameLw() {
-    }
-
-    @Override
-    public Rect getFrameLw() {
-        return mWindowFrames.mParentFrame;
-    }
-
-    @Override
-    public Rect getDisplayFrameLw() {
-        return mWindowFrames.mDisplayFrame;
-    }
-
-    @Override
-    public Rect getOverscanFrameLw() {
-        return mWindowFrames.mOverscanFrame;
-    }
-
-    @Override
-    public Rect getContentFrameLw() {
-        return mWindowFrames.mContentFrame;
-    }
-
-    @Override
-    public Rect getVisibleFrameLw() {
-        return mWindowFrames.mVisibleFrame;
-    }
-
-    public Rect getStableFrame() {
-        return mWindowFrames.mStableFrame;
-    }
-
-    public Rect getDecorFrame() {
-        return mWindowFrames.mDecorFrame;
-    }
-
-    @Override
-    public boolean getGivenInsetsPendingLw() {
-        throw new UnsupportedOperationException("not implemented");
-    }
-
-    @Override
-    public Rect getGivenContentInsetsLw() {
-        throw new UnsupportedOperationException("not implemented");
-    }
-
-    @Override
-    public Rect getGivenVisibleInsetsLw() {
-        throw new UnsupportedOperationException("not implemented");
-    }
-
-    @Override
-    public WindowManager.LayoutParams getAttrs() {
-        return attrs;
-    }
-
-    @Override
-    public boolean getNeedsMenuLw(WindowManagerPolicy.WindowState bottom) {
-        throw new UnsupportedOperationException("not implemented");
-    }
-
-    @Override
-    public int getSystemUiVisibility() {
-        return attrs.systemUiVisibility | attrs.subtreeSystemUiVisibility;
-    }
-
-    @Override
-    public int getSurfaceLayer() {
-        return surfaceLayer;
-    }
-
-    @Override
-    public int getBaseType() {
-        throw new UnsupportedOperationException("not implemented");
-    }
-
-    @Override
-    public IApplicationToken getAppToken() {
-        throw new UnsupportedOperationException("not implemented");
-    }
-
-    @Override
-    public boolean isVoiceInteraction() {
-        return isVoiceInteraction;
-    }
-
-    @Override
-    public boolean hasAppShownWindows() {
-        throw new UnsupportedOperationException("not implemented");
-    }
-
-    @Override
-    public boolean isVisibleLw() {
-        return visible && policyVisible;
-    }
-
-    @Override
-    public boolean isDisplayedLw() {
-        return isVisibleLw();
-    }
-
-    @Override
-    public boolean isAnimatingLw() {
-        return false;
-    }
-
-    @Override
-    public boolean canAffectSystemUiFlags() {
-        throw new UnsupportedOperationException("not implemented");
-    }
-
-    @Override
-    public boolean isGoneForLayoutLw() {
-        throw new UnsupportedOperationException("not implemented");
-    }
-
-    @Override
-    public boolean isDrawnLw() {
-        return true;
-    }
-
-    @Override
-    public boolean hasDrawnLw() {
-        return true;
-    }
-
-    @Override
-    public boolean hideLw(boolean doAnimation) {
-        if (!policyVisible) {
-            return false;
-        }
-        policyVisible = false;
-        return true;
-    }
-
-    @Override
-    public boolean showLw(boolean doAnimation) {
-        if (policyVisible) {
-            return false;
-        }
-        policyVisible = true;
-        return true;
-    }
-
-    @Override
-    public boolean isAlive() {
-        return true;
-    }
-
-    @Override
-    public boolean isDefaultDisplay() {
-        return displayId == Display.DEFAULT_DISPLAY;
-    }
-
-    @Override
-    public boolean isDimming() {
-        return isDimming;
-    }
-
-    @Override
-    public int getWindowingMode() {
-        throw new UnsupportedOperationException("not implemented");
-    }
-
-    @Override
-    public boolean isInMultiWindowMode() {
-        return inMultiWindowMode;
-    }
-
-    @Override
-    public int getRotationAnimationHint() {
-        throw new UnsupportedOperationException("not implemented");
-    }
-
-    @Override
-    public boolean isInputMethodWindow() {
-        throw new UnsupportedOperationException("not implemented");
-    }
-
-    @Override
-    public int getDisplayId() {
-        return displayId;
-    }
-
-    @Override
-    public boolean canAcquireSleepToken() {
-        throw new UnsupportedOperationException("not implemented");
-    }
-
-    @Override
-    public boolean canReceiveKeys() {
-        return false;
-    }
-
-    @Override
-    public void writeIdentifierToProto(ProtoOutputStream proto, long fieldId) {
-        throw new UnsupportedOperationException("not implemented");
-    }
-
-    @Override
-    public WindowFrames getWindowFrames() {
-        return mWindowFrames;
-    }
-
-    @Override
-    public boolean isInputMethodTarget() {
-        return false;
-    }
-}
diff --git a/services/tests/wmtests/src/com/android/server/policy/PhoneWindowManagerLayoutTest.java b/services/tests/wmtests/src/com/android/server/policy/PhoneWindowManagerLayoutTest.java
deleted file mode 100644
index e8f767a..0000000
--- a/services/tests/wmtests/src/com/android/server/policy/PhoneWindowManagerLayoutTest.java
+++ /dev/null
@@ -1,395 +0,0 @@
-/*
- * Copyright (C) 2017 The Android Open Source Project
- *
- * Licensed under the Apache License, Version 2.0 (the "License");
- * you may not use this file except in compliance with the License.
- * You may obtain a copy of the License at
- *
- *      http://www.apache.org/licenses/LICENSE-2.0
- *
- * Unless required by applicable law or agreed to in writing, software
- * distributed under the License is distributed on an "AS IS" BASIS,
- * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
- * See the License for the specific language governing permissions and
- * limitations under the License.
- */
-
-package com.android.server.policy;
-
-import static android.view.Surface.ROTATION_270;
-import static android.view.Surface.ROTATION_90;
-import static android.view.View.SYSTEM_UI_FLAG_FULLSCREEN;
-import static android.view.View.SYSTEM_UI_FLAG_LAYOUT_FULLSCREEN;
-import static android.view.ViewGroup.LayoutParams.MATCH_PARENT;
-import static android.view.WindowManager.LayoutParams.FLAG_DRAWS_SYSTEM_BAR_BACKGROUNDS;
-import static android.view.WindowManager.LayoutParams.FLAG_LAYOUT_INSET_DECOR;
-import static android.view.WindowManager.LayoutParams.FLAG_LAYOUT_IN_SCREEN;
-import static android.view.WindowManager.LayoutParams.LAYOUT_IN_DISPLAY_CUTOUT_MODE_ALWAYS;
-import static android.view.WindowManager.LayoutParams.LAYOUT_IN_DISPLAY_CUTOUT_MODE_NEVER;
-import static android.view.WindowManager.LayoutParams.PRIVATE_FLAG_FORCE_DRAW_STATUS_BAR_BACKGROUND;
-import static android.view.WindowManager.LayoutParams.PRIVATE_FLAG_IS_SCREEN_DECOR;
-import static android.view.WindowManager.LayoutParams.TYPE_APPLICATION;
-import static android.view.WindowManager.LayoutParams.TYPE_APPLICATION_OVERLAY;
-
-import static org.hamcrest.Matchers.equalTo;
-import static org.hamcrest.Matchers.is;
-import static org.junit.Assert.assertEquals;
-import static org.junit.Assert.assertThat;
-
-import android.graphics.PixelFormat;
-import android.graphics.Rect;
-import android.platform.test.annotations.Presubmit;
-import android.view.DisplayCutout;
-import android.view.WindowManager;
-
-import androidx.test.filters.SmallTest;
-
-import org.junit.Before;
-import org.junit.Test;
-
-/**
- * Build/Install/Run:
- *  atest WmTests:PhoneWindowManagerLayoutTest
- */
-@SmallTest
-@Presubmit
-public class PhoneWindowManagerLayoutTest extends PhoneWindowManagerTestBase {
-
-    private FakeWindowState mAppWindow;
-
-    @Before
-    public void setUp() throws Exception {
-        mAppWindow = new FakeWindowState();
-        mAppWindow.attrs = new WindowManager.LayoutParams(MATCH_PARENT, MATCH_PARENT,
-                TYPE_APPLICATION,
-                FLAG_LAYOUT_IN_SCREEN | FLAG_LAYOUT_INSET_DECOR | FLAG_DRAWS_SYSTEM_BAR_BACKGROUNDS,
-                PixelFormat.TRANSLUCENT);
-
-        addStatusBar();
-        addNavigationBar();
-    }
-
-    @Test
-    public void layoutWindowLw_appDrawsBars() {
-        mAppWindow.attrs.flags |= FLAG_DRAWS_SYSTEM_BAR_BACKGROUNDS;
-        mPolicy.addWindow(mAppWindow);
-
-        mPolicy.beginLayoutLw(mFrames, 0 /* UI mode */);
-        mPolicy.layoutWindowLw(mAppWindow, null, mFrames);
-
-        assertInsetByTopBottom(mAppWindow.getFrameLw(), 0, 0);
-        assertInsetByTopBottom(mAppWindow.getStableFrame(), STATUS_BAR_HEIGHT, NAV_BAR_HEIGHT);
-        assertInsetByTopBottom(mAppWindow.getContentFrameLw(), STATUS_BAR_HEIGHT, NAV_BAR_HEIGHT);
-        assertInsetByTopBottom(mAppWindow.getDecorFrame(), 0, 0);
-        assertInsetBy(mAppWindow.getDisplayFrameLw(), 0, 0, 0, 0);
-    }
-
-    @Test
-    public void layoutWindowLw_appWontDrawBars() {
-        mAppWindow.attrs.flags &= ~FLAG_DRAWS_SYSTEM_BAR_BACKGROUNDS;
-        mPolicy.addWindow(mAppWindow);
-
-        mPolicy.beginLayoutLw(mFrames, 0 /* UI mode */);
-        mPolicy.layoutWindowLw(mAppWindow, null, mFrames);
-
-        assertInsetByTopBottom(mAppWindow.getFrameLw(), 0, NAV_BAR_HEIGHT);
-        assertInsetByTopBottom(mAppWindow.getStableFrame(), STATUS_BAR_HEIGHT, NAV_BAR_HEIGHT);
-        assertInsetByTopBottom(mAppWindow.getContentFrameLw(), STATUS_BAR_HEIGHT, NAV_BAR_HEIGHT);
-        assertInsetByTopBottom(mAppWindow.getDecorFrame(), STATUS_BAR_HEIGHT, NAV_BAR_HEIGHT);
-        assertInsetByTopBottom(mAppWindow.getDisplayFrameLw(), 0, NAV_BAR_HEIGHT);
-    }
-
-    @Test
-    public void layoutWindowLw_appWontDrawBars_forceStatus() {
-        mAppWindow.attrs.flags &= ~FLAG_DRAWS_SYSTEM_BAR_BACKGROUNDS;
-        mAppWindow.attrs.privateFlags |= PRIVATE_FLAG_FORCE_DRAW_STATUS_BAR_BACKGROUND;
-        mPolicy.addWindow(mAppWindow);
-
-        mPolicy.beginLayoutLw(mFrames, 0 /* UI mode */);
-        mPolicy.layoutWindowLw(mAppWindow, null, mFrames);
-
-        assertInsetByTopBottom(mAppWindow.getFrameLw(), 0, NAV_BAR_HEIGHT);
-        assertInsetByTopBottom(mAppWindow.getStableFrame(), STATUS_BAR_HEIGHT, NAV_BAR_HEIGHT);
-        assertInsetByTopBottom(mAppWindow.getContentFrameLw(), STATUS_BAR_HEIGHT, NAV_BAR_HEIGHT);
-        assertInsetByTopBottom(mAppWindow.getDecorFrame(), 0, NAV_BAR_HEIGHT);
-        assertInsetByTopBottom(mAppWindow.getDisplayFrameLw(), 0, NAV_BAR_HEIGHT);
-    }
-
-    @Test
-    public void addingWindow_doesNotTamperWithSysuiFlags() {
-        mAppWindow.attrs.flags |= FLAG_DRAWS_SYSTEM_BAR_BACKGROUNDS;
-        mPolicy.addWindow(mAppWindow);
-
-        assertEquals(0, mAppWindow.attrs.systemUiVisibility);
-        assertEquals(0, mAppWindow.attrs.subtreeSystemUiVisibility);
-    }
-
-    @Test
-    public void layoutWindowLw_withDisplayCutout() {
-        addDisplayCutout();
-
-        mPolicy.addWindow(mAppWindow);
-
-        mPolicy.beginLayoutLw(mFrames, 0 /* UI mode */);
-        mPolicy.layoutWindowLw(mAppWindow, null, mFrames);
-
-        assertInsetByTopBottom(mAppWindow.getFrameLw(), 0, 0);
-        assertInsetByTopBottom(mAppWindow.getStableFrame(), STATUS_BAR_HEIGHT, NAV_BAR_HEIGHT);
-        assertInsetByTopBottom(mAppWindow.getContentFrameLw(), STATUS_BAR_HEIGHT, NAV_BAR_HEIGHT);
-        assertInsetByTopBottom(mAppWindow.getDecorFrame(), 0, 0);
-        assertInsetByTopBottom(mAppWindow.getDisplayFrameLw(), 0, 0);
-    }
-
-    @Test
-    public void layoutWindowLw_withhDisplayCutout_never() {
-        addDisplayCutout();
-
-        mAppWindow.attrs.layoutInDisplayCutoutMode = LAYOUT_IN_DISPLAY_CUTOUT_MODE_NEVER;
-        mPolicy.addWindow(mAppWindow);
-
-        mPolicy.beginLayoutLw(mFrames, 0 /* UI mode */);
-        mPolicy.layoutWindowLw(mAppWindow, null, mFrames);
-
-        assertInsetByTopBottom(mAppWindow.getFrameLw(), STATUS_BAR_HEIGHT, 0);
-        assertInsetByTopBottom(mAppWindow.getStableFrame(), STATUS_BAR_HEIGHT, NAV_BAR_HEIGHT);
-        assertInsetByTopBottom(mAppWindow.getContentFrameLw(), STATUS_BAR_HEIGHT, NAV_BAR_HEIGHT);
-        assertInsetByTopBottom(mAppWindow.getDecorFrame(), 0, 0);
-        assertInsetByTopBottom(mAppWindow.getDisplayFrameLw(), STATUS_BAR_HEIGHT, 0);
-    }
-
-    @Test
-    public void layoutWindowLw_withDisplayCutout_layoutFullscreen() {
-        addDisplayCutout();
-
-        mAppWindow.attrs.subtreeSystemUiVisibility |= SYSTEM_UI_FLAG_LAYOUT_FULLSCREEN;
-        mPolicy.addWindow(mAppWindow);
-
-        mPolicy.beginLayoutLw(mFrames, 0 /* UI mode */);
-        mPolicy.layoutWindowLw(mAppWindow, null, mFrames);
-
-        assertInsetByTopBottom(mAppWindow.getFrameLw(), 0, 0);
-        assertInsetByTopBottom(mAppWindow.getStableFrame(), STATUS_BAR_HEIGHT, NAV_BAR_HEIGHT);
-        assertInsetByTopBottom(mAppWindow.getContentFrameLw(), STATUS_BAR_HEIGHT, NAV_BAR_HEIGHT);
-        assertInsetByTopBottom(mAppWindow.getDecorFrame(), 0, 0);
-        assertInsetBy(mAppWindow.getDisplayFrameLw(), 0, 0, 0, 0);
-    }
-
-    @Test
-    public void layoutWindowLw_withDisplayCutout_fullscreen() {
-        addDisplayCutout();
-
-        mAppWindow.attrs.subtreeSystemUiVisibility |= SYSTEM_UI_FLAG_FULLSCREEN;
-        mPolicy.addWindow(mAppWindow);
-
-        mPolicy.beginLayoutLw(mFrames, 0 /* UI mode */);
-        mPolicy.layoutWindowLw(mAppWindow, null, mFrames);
-
-        assertInsetByTopBottom(mAppWindow.getFrameLw(), STATUS_BAR_HEIGHT, 0);
-        assertInsetByTopBottom(mAppWindow.getStableFrame(), STATUS_BAR_HEIGHT, NAV_BAR_HEIGHT);
-        assertInsetByTopBottom(mAppWindow.getContentFrameLw(), STATUS_BAR_HEIGHT, NAV_BAR_HEIGHT);
-        assertInsetByTopBottom(mAppWindow.getDecorFrame(), 0, 0);
-        assertInsetByTopBottom(mAppWindow.getDisplayFrameLw(), STATUS_BAR_HEIGHT, 0);
-    }
-
-    @Test
-    public void layoutWindowLw_withDisplayCutout_fullscreenInCutout() {
-        addDisplayCutout();
-
-        mAppWindow.attrs.subtreeSystemUiVisibility |= SYSTEM_UI_FLAG_FULLSCREEN;
-        mAppWindow.attrs.layoutInDisplayCutoutMode = LAYOUT_IN_DISPLAY_CUTOUT_MODE_ALWAYS;
-        mPolicy.addWindow(mAppWindow);
-
-        mPolicy.beginLayoutLw(mFrames, 0 /* UI mode */);
-        mPolicy.layoutWindowLw(mAppWindow, null, mFrames);
-
-        assertInsetByTopBottom(mAppWindow.getFrameLw(), 0, 0);
-        assertInsetByTopBottom(mAppWindow.getStableFrame(), STATUS_BAR_HEIGHT, NAV_BAR_HEIGHT);
-        assertInsetByTopBottom(mAppWindow.getContentFrameLw(), STATUS_BAR_HEIGHT, NAV_BAR_HEIGHT);
-        assertInsetByTopBottom(mAppWindow.getDecorFrame(), 0, 0);
-        assertInsetByTopBottom(mAppWindow.getDisplayFrameLw(), 0, 0);
-    }
-
-
-    @Test
-    public void layoutWindowLw_withDisplayCutout_landscape() {
-        addDisplayCutout();
-        setRotation(ROTATION_90);
-        mPolicy.addWindow(mAppWindow);
-
-        mPolicy.beginLayoutLw(mFrames, 0 /* UI mode */);
-        mPolicy.layoutWindowLw(mAppWindow, null, mFrames);
-
-        assertInsetBy(mAppWindow.getFrameLw(), DISPLAY_CUTOUT_HEIGHT, 0, 0, 0);
-        assertInsetBy(mAppWindow.getStableFrame(), 0, STATUS_BAR_HEIGHT, NAV_BAR_HEIGHT, 0);
-        assertInsetBy(mAppWindow.getContentFrameLw(),
-                DISPLAY_CUTOUT_HEIGHT, STATUS_BAR_HEIGHT, NAV_BAR_HEIGHT, 0);
-        assertInsetBy(mAppWindow.getDecorFrame(), 0, 0, 0, 0);
-        assertInsetBy(mAppWindow.getDisplayFrameLw(), DISPLAY_CUTOUT_HEIGHT, 0, 0, 0);
-    }
-
-    @Test
-    public void layoutWindowLw_withDisplayCutout_seascape() {
-        addDisplayCutout();
-        setRotation(ROTATION_270);
-        mPolicy.addWindow(mAppWindow);
-
-        mPolicy.beginLayoutLw(mFrames, 0 /* UI mode */);
-        mPolicy.layoutWindowLw(mAppWindow, null, mFrames);
-
-        assertInsetBy(mAppWindow.getFrameLw(), 0, 0, DISPLAY_CUTOUT_HEIGHT, 0);
-        assertInsetBy(mAppWindow.getStableFrame(), NAV_BAR_HEIGHT, STATUS_BAR_HEIGHT, 0, 0);
-        assertInsetBy(mAppWindow.getContentFrameLw(),
-                NAV_BAR_HEIGHT, STATUS_BAR_HEIGHT, DISPLAY_CUTOUT_HEIGHT, 0);
-        assertInsetBy(mAppWindow.getDecorFrame(), 0, 0, 0, 0);
-        assertInsetBy(mAppWindow.getDisplayFrameLw(), 0, 0, DISPLAY_CUTOUT_HEIGHT, 0);
-    }
-
-    @Test
-    public void layoutWindowLw_withDisplayCutout_fullscreen_landscape() {
-        addDisplayCutout();
-        setRotation(ROTATION_90);
-
-        mAppWindow.attrs.subtreeSystemUiVisibility |= SYSTEM_UI_FLAG_LAYOUT_FULLSCREEN;
-        mPolicy.addWindow(mAppWindow);
-
-        mPolicy.beginLayoutLw(mFrames, 0 /* UI mode */);
-        mPolicy.layoutWindowLw(mAppWindow, null, mFrames);
-
-        assertInsetBy(mAppWindow.getFrameLw(), DISPLAY_CUTOUT_HEIGHT, 0, 0, 0);
-        assertInsetBy(mAppWindow.getStableFrame(), 0, STATUS_BAR_HEIGHT, NAV_BAR_HEIGHT, 0);
-        assertInsetBy(mAppWindow.getContentFrameLw(),
-                DISPLAY_CUTOUT_HEIGHT, STATUS_BAR_HEIGHT, NAV_BAR_HEIGHT, 0);
-        assertInsetBy(mAppWindow.getDecorFrame(), 0, 0, 0, 0);
-    }
-
-    @Test
-    public void layoutWindowLw_withDisplayCutout_floatingInScreen() {
-        addDisplayCutout();
-
-        mAppWindow.attrs.flags = FLAG_LAYOUT_IN_SCREEN;
-        mAppWindow.attrs.type = TYPE_APPLICATION_OVERLAY;
-        mAppWindow.attrs.width = DISPLAY_WIDTH;
-        mAppWindow.attrs.height = DISPLAY_HEIGHT;
-        mPolicy.addWindow(mAppWindow);
-
-        mPolicy.beginLayoutLw(mFrames, 0 /* UI mode */);
-        mPolicy.layoutWindowLw(mAppWindow, null, mFrames);
-
-        assertInsetByTopBottom(mAppWindow.getFrameLw(), 0, NAV_BAR_HEIGHT);
-        assertInsetByTopBottom(mAppWindow.getDisplayFrameLw(), STATUS_BAR_HEIGHT, NAV_BAR_HEIGHT);
-    }
-
-    @Test
-    public void layoutWindowLw_withDisplayCutout_fullscreenInCutout_landscape() {
-        addDisplayCutout();
-        setRotation(ROTATION_90);
-
-        mAppWindow.attrs.subtreeSystemUiVisibility |= SYSTEM_UI_FLAG_LAYOUT_FULLSCREEN;
-        mAppWindow.attrs.layoutInDisplayCutoutMode = LAYOUT_IN_DISPLAY_CUTOUT_MODE_ALWAYS;
-        mPolicy.addWindow(mAppWindow);
-
-        mPolicy.beginLayoutLw(mFrames, 0 /* UI mode */);
-        mPolicy.layoutWindowLw(mAppWindow, null, mFrames);
-
-        assertInsetBy(mAppWindow.getFrameLw(), 0, 0, 0, 0);
-        assertInsetBy(mAppWindow.getStableFrame(), 0, STATUS_BAR_HEIGHT, NAV_BAR_HEIGHT, 0);
-        assertInsetBy(mAppWindow.getContentFrameLw(),
-                DISPLAY_CUTOUT_HEIGHT, STATUS_BAR_HEIGHT, NAV_BAR_HEIGHT, 0);
-        assertInsetBy(mAppWindow.getDecorFrame(), 0, 0, 0, 0);
-    }
-
-    @Test
-    public void layoutHint_screenDecorWindow() {
-        addDisplayCutout();
-        mAppWindow.attrs.privateFlags |= PRIVATE_FLAG_IS_SCREEN_DECOR;
-
-        mPolicy.beginLayoutLw(mFrames, 0 /* UI mode */);
-
-        final Rect frame = new Rect();
-        final Rect content = new Rect();
-        final Rect stable = new Rect();
-        final Rect outsets = new Rect();
-        final DisplayCutout.ParcelableWrapper cutout = new DisplayCutout.ParcelableWrapper();
-        mPolicy.getLayoutHintLw(mAppWindow.attrs, null /* taskBounds */, mFrames,
-                false /* floatingStack */, frame, content, stable, outsets, cutout);
-
-        assertThat(frame, equalTo(mFrames.mUnrestricted));
-        assertThat(content, equalTo(new Rect()));
-        assertThat(stable, equalTo(new Rect()));
-        assertThat(outsets, equalTo(new Rect()));
-        assertThat(cutout.get(), equalTo(DisplayCutout.NO_CUTOUT));
-    }
-
-    @Test
-    public void layoutHint_appWindow() {
-        // Initialize DisplayFrames
-        mPolicy.beginLayoutLw(mFrames, 0 /* UI mode */);
-
-        final Rect outFrame = new Rect();
-        final Rect outContentInsets = new Rect();
-        final Rect outStableInsets = new Rect();
-        final Rect outOutsets = new Rect();
-        final DisplayCutout.ParcelableWrapper outDisplayCutout =
-                new DisplayCutout.ParcelableWrapper();
-
-        mPolicy.getLayoutHintLw(mAppWindow.attrs, null, mFrames, false /* floatingStack */,
-                outFrame, outContentInsets, outStableInsets, outOutsets, outDisplayCutout);
-
-        assertThat(outFrame, is(mFrames.mUnrestricted));
-        assertThat(outContentInsets, is(new Rect(0, STATUS_BAR_HEIGHT, 0, NAV_BAR_HEIGHT)));
-        assertThat(outStableInsets, is(new Rect(0, STATUS_BAR_HEIGHT, 0, NAV_BAR_HEIGHT)));
-        assertThat(outOutsets, is(new Rect()));
-        assertThat(outDisplayCutout, is(new DisplayCutout.ParcelableWrapper()));
-    }
-
-    @Test
-    public void layoutHint_appWindowInTask() {
-        // Initialize DisplayFrames
-        mPolicy.beginLayoutLw(mFrames, 0 /* UI mode */);
-
-        final Rect taskBounds = new Rect(100, 100, 200, 200);
-
-        final Rect outFrame = new Rect();
-        final Rect outContentInsets = new Rect();
-        final Rect outStableInsets = new Rect();
-        final Rect outOutsets = new Rect();
-        final DisplayCutout.ParcelableWrapper outDisplayCutout =
-                new DisplayCutout.ParcelableWrapper();
-
-        mPolicy.getLayoutHintLw(mAppWindow.attrs, taskBounds, mFrames, false /* floatingStack */,
-                outFrame, outContentInsets, outStableInsets, outOutsets, outDisplayCutout);
-
-        assertThat(outFrame, is(taskBounds));
-        assertThat(outContentInsets, is(new Rect()));
-        assertThat(outStableInsets, is(new Rect()));
-        assertThat(outOutsets, is(new Rect()));
-        assertThat(outDisplayCutout, is(new DisplayCutout.ParcelableWrapper()));
-    }
-
-    @Test
-    public void layoutHint_appWindowInTask_outsideContentFrame() {
-        // Initialize DisplayFrames
-        mPolicy.beginLayoutLw(mFrames, 0 /* UI mode */);
-
-        // Task is in the nav bar area (usually does not happen, but this is similar enough to the
-        // possible overlap with the IME)
-        final Rect taskBounds = new Rect(100, mFrames.mContent.bottom + 1,
-                200, mFrames.mContent.bottom + 10);
-
-        final Rect outFrame = new Rect();
-        final Rect outContentInsets = new Rect();
-        final Rect outStableInsets = new Rect();
-        final Rect outOutsets = new Rect();
-        final DisplayCutout.ParcelableWrapper outDisplayCutout =
-                new DisplayCutout.ParcelableWrapper();
-
-        mPolicy.getLayoutHintLw(mAppWindow.attrs, taskBounds, mFrames, true /* floatingStack */,
-                outFrame, outContentInsets, outStableInsets, outOutsets, outDisplayCutout);
-
-        assertThat(outFrame, is(taskBounds));
-        assertThat(outContentInsets, is(new Rect()));
-        assertThat(outStableInsets, is(new Rect()));
-        assertThat(outOutsets, is(new Rect()));
-        assertThat(outDisplayCutout, is(new DisplayCutout.ParcelableWrapper()));
-    }
-}
diff --git a/services/tests/wmtests/src/com/android/server/policy/PhoneWindowManagerTest.java b/services/tests/wmtests/src/com/android/server/policy/PhoneWindowManagerTest.java
deleted file mode 100644
index 6c44d65..0000000
--- a/services/tests/wmtests/src/com/android/server/policy/PhoneWindowManagerTest.java
+++ /dev/null
@@ -1,255 +0,0 @@
-/*
- * Copyright (C) 2018 The Android Open Source Project
- *
- * Licensed under the Apache License, Version 2.0 (the "License");
- * you may not use this file except in compliance with the License.
- * You may obtain a copy of the License at
- *
- *      http://www.apache.org/licenses/LICENSE-2.0
- *
- * Unless required by applicable law or agreed to in writing, software
- * distributed under the License is distributed on an "AS IS" BASIS,
- * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
- * See the License for the specific language governing permissions and
- * limitations under the License.
- */
-
-package com.android.server.policy;
-
-import static android.view.View.SYSTEM_UI_FLAG_LIGHT_NAVIGATION_BAR;
-import static android.view.ViewGroup.LayoutParams.MATCH_PARENT;
-import static android.view.ViewGroup.LayoutParams.WRAP_CONTENT;
-import static android.view.WindowManager.DOCKED_BOTTOM;
-import static android.view.WindowManager.DOCKED_LEFT;
-import static android.view.WindowManager.DOCKED_RIGHT;
-import static android.view.WindowManager.DOCKED_TOP;
-import static android.view.WindowManager.LayoutParams.FLAG_ALT_FOCUSABLE_IM;
-import static android.view.WindowManager.LayoutParams.FLAG_DIM_BEHIND;
-import static android.view.WindowManager.LayoutParams.FLAG_DRAWS_SYSTEM_BAR_BACKGROUNDS;
-import static android.view.WindowManager.LayoutParams.FLAG_LAYOUT_INSET_DECOR;
-import static android.view.WindowManager.LayoutParams.FLAG_LAYOUT_IN_SCREEN;
-import static android.view.WindowManager.LayoutParams.FLAG_NOT_FOCUSABLE;
-import static android.view.WindowManager.LayoutParams.TYPE_APPLICATION;
-import static android.view.WindowManager.LayoutParams.TYPE_BASE_APPLICATION;
-import static android.view.WindowManager.LayoutParams.TYPE_INPUT_METHOD;
-
-import static com.android.server.policy.WindowManagerPolicy.NAV_BAR_BOTTOM;
-import static com.android.server.policy.WindowManagerPolicy.NAV_BAR_LEFT;
-import static com.android.server.policy.WindowManagerPolicy.NAV_BAR_RIGHT;
-
-import static org.junit.Assert.assertEquals;
-import static org.junit.Assert.assertFalse;
-import static org.junit.Assert.assertNull;
-import static org.junit.Assert.assertTrue;
-
-import android.graphics.PixelFormat;
-import android.platform.test.annotations.Presubmit;
-import android.view.WindowManager;
-
-import androidx.test.filters.SmallTest;
-
-import org.junit.Test;
-
-/**
- * Build/Install/Run:
- *  atest WmTests:PhoneWindowManagerTest
- */
-@SmallTest
-@Presubmit
-public class PhoneWindowManagerTest {
-
-    private static FakeWindowState createOpaqueFullscreen(boolean hasLightNavBar) {
-        final FakeWindowState state = new FakeWindowState();
-        state.attrs = new WindowManager.LayoutParams(MATCH_PARENT, MATCH_PARENT,
-                TYPE_BASE_APPLICATION,
-                FLAG_LAYOUT_IN_SCREEN | FLAG_LAYOUT_INSET_DECOR | FLAG_DRAWS_SYSTEM_BAR_BACKGROUNDS,
-                PixelFormat.OPAQUE);
-        state.attrs.subtreeSystemUiVisibility =
-                hasLightNavBar ? SYSTEM_UI_FLAG_LIGHT_NAVIGATION_BAR : 0;
-        return state;
-    }
-
-    private static FakeWindowState createDimmingDialogWindow(boolean canBeImTarget) {
-        final FakeWindowState state = new FakeWindowState();
-        state.attrs = new WindowManager.LayoutParams(WRAP_CONTENT, WRAP_CONTENT,
-                TYPE_APPLICATION,
-                FLAG_DIM_BEHIND  | (canBeImTarget ? 0 : FLAG_ALT_FOCUSABLE_IM),
-                PixelFormat.TRANSLUCENT);
-        state.isDimming = true;
-        return state;
-    }
-
-    private static FakeWindowState createInputMethodWindow(boolean visible, boolean drawNavBar,
-            boolean hasLightNavBar) {
-        final FakeWindowState state = new FakeWindowState();
-        state.attrs = new WindowManager.LayoutParams(MATCH_PARENT, MATCH_PARENT,
-                TYPE_INPUT_METHOD,
-                FLAG_NOT_FOCUSABLE | FLAG_LAYOUT_IN_SCREEN
-                        | (drawNavBar ? FLAG_DRAWS_SYSTEM_BAR_BACKGROUNDS : 0),
-                PixelFormat.TRANSPARENT);
-        state.attrs.subtreeSystemUiVisibility =
-                hasLightNavBar ? SYSTEM_UI_FLAG_LIGHT_NAVIGATION_BAR : 0;
-        state.visible = visible;
-        state.policyVisible = visible;
-        return state;
-    }
-
-
-    @Test
-    public void testChooseNavigationColorWindowLw() {
-        final FakeWindowState opaque = createOpaqueFullscreen(false);
-
-        final FakeWindowState dimmingImTarget = createDimmingDialogWindow(true);
-        final FakeWindowState dimmingNonImTarget = createDimmingDialogWindow(false);
-
-        final FakeWindowState visibleIme = createInputMethodWindow(true, true, false);
-        final FakeWindowState invisibleIme = createInputMethodWindow(false, true, false);
-        final FakeWindowState imeNonDrawNavBar = createInputMethodWindow(true, false, false);
-
-        // If everything is null, return null
-        assertNull(null, PhoneWindowManager.chooseNavigationColorWindowLw(
-                null, null, null, NAV_BAR_BOTTOM));
-
-        assertEquals(opaque, PhoneWindowManager.chooseNavigationColorWindowLw(
-                opaque, opaque, null, NAV_BAR_BOTTOM));
-        assertEquals(dimmingImTarget, PhoneWindowManager.chooseNavigationColorWindowLw(
-                opaque, dimmingImTarget, null, NAV_BAR_BOTTOM));
-        assertEquals(dimmingNonImTarget, PhoneWindowManager.chooseNavigationColorWindowLw(
-                opaque, dimmingNonImTarget, null, NAV_BAR_BOTTOM));
-
-        assertEquals(visibleIme, PhoneWindowManager.chooseNavigationColorWindowLw(
-                null, null, visibleIme, NAV_BAR_BOTTOM));
-        assertEquals(visibleIme, PhoneWindowManager.chooseNavigationColorWindowLw(
-                null, dimmingImTarget, visibleIme, NAV_BAR_BOTTOM));
-        assertEquals(dimmingNonImTarget, PhoneWindowManager.chooseNavigationColorWindowLw(
-                null, dimmingNonImTarget, visibleIme, NAV_BAR_BOTTOM));
-        assertEquals(visibleIme, PhoneWindowManager.chooseNavigationColorWindowLw(
-                opaque, opaque, visibleIme, NAV_BAR_BOTTOM));
-        assertEquals(visibleIme, PhoneWindowManager.chooseNavigationColorWindowLw(
-                opaque, dimmingImTarget, visibleIme, NAV_BAR_BOTTOM));
-        assertEquals(dimmingNonImTarget, PhoneWindowManager.chooseNavigationColorWindowLw(
-                opaque, dimmingNonImTarget, visibleIme, NAV_BAR_BOTTOM));
-
-        assertEquals(opaque, PhoneWindowManager.chooseNavigationColorWindowLw(
-                opaque, opaque, invisibleIme, NAV_BAR_BOTTOM));
-        assertEquals(opaque, PhoneWindowManager.chooseNavigationColorWindowLw(
-                opaque, opaque, invisibleIme, NAV_BAR_BOTTOM));
-        assertEquals(opaque, PhoneWindowManager.chooseNavigationColorWindowLw(
-                opaque, opaque, visibleIme, NAV_BAR_RIGHT));
-
-        // Only IME windows that have FLAG_DRAWS_SYSTEM_BAR_BACKGROUNDS should be navigation color
-        // window.
-        assertEquals(opaque, PhoneWindowManager.chooseNavigationColorWindowLw(
-                opaque, opaque, imeNonDrawNavBar, NAV_BAR_BOTTOM));
-        assertEquals(dimmingImTarget, PhoneWindowManager.chooseNavigationColorWindowLw(
-                opaque, dimmingImTarget, imeNonDrawNavBar, NAV_BAR_BOTTOM));
-        assertEquals(dimmingNonImTarget, PhoneWindowManager.chooseNavigationColorWindowLw(
-                opaque, dimmingNonImTarget, imeNonDrawNavBar, NAV_BAR_BOTTOM));
-    }
-
-    @Test
-    public void testUpdateLightNavigationBarLw() {
-        final FakeWindowState opaqueDarkNavBar = createOpaqueFullscreen(false);
-        final FakeWindowState opaqueLightNavBar = createOpaqueFullscreen(true);
-
-        final FakeWindowState dimming = createDimmingDialogWindow(false);
-
-        final FakeWindowState imeDrawDarkNavBar = createInputMethodWindow(true, true, false);
-        final FakeWindowState imeDrawLightNavBar = createInputMethodWindow(true, true, true);
-
-        assertEquals(SYSTEM_UI_FLAG_LIGHT_NAVIGATION_BAR,
-                PhoneWindowManager.updateLightNavigationBarLw(
-                        SYSTEM_UI_FLAG_LIGHT_NAVIGATION_BAR, null, null,
-                        null, null));
-
-        // Opaque top fullscreen window overrides SYSTEM_UI_FLAG_LIGHT_NAVIGATION_BAR flag.
-        assertEquals(0, PhoneWindowManager.updateLightNavigationBarLw(
-                0, opaqueDarkNavBar, opaqueDarkNavBar, null, opaqueDarkNavBar));
-        assertEquals(0, PhoneWindowManager.updateLightNavigationBarLw(
-                SYSTEM_UI_FLAG_LIGHT_NAVIGATION_BAR, opaqueDarkNavBar, opaqueDarkNavBar, null,
-                opaqueDarkNavBar));
-        assertEquals(SYSTEM_UI_FLAG_LIGHT_NAVIGATION_BAR,
-                PhoneWindowManager.updateLightNavigationBarLw(0, opaqueLightNavBar,
-                        opaqueLightNavBar, null, opaqueLightNavBar));
-        assertEquals(SYSTEM_UI_FLAG_LIGHT_NAVIGATION_BAR,
-                PhoneWindowManager.updateLightNavigationBarLw(SYSTEM_UI_FLAG_LIGHT_NAVIGATION_BAR,
-                        opaqueLightNavBar, opaqueLightNavBar, null, opaqueLightNavBar));
-
-        // Dimming window clears SYSTEM_UI_FLAG_LIGHT_NAVIGATION_BAR.
-        assertEquals(0, PhoneWindowManager.updateLightNavigationBarLw(
-                0, opaqueDarkNavBar, dimming, null, dimming));
-        assertEquals(0, PhoneWindowManager.updateLightNavigationBarLw(
-                0, opaqueLightNavBar, dimming, null, dimming));
-        assertEquals(0, PhoneWindowManager.updateLightNavigationBarLw(
-                SYSTEM_UI_FLAG_LIGHT_NAVIGATION_BAR, opaqueDarkNavBar, dimming, null, dimming));
-        assertEquals(0, PhoneWindowManager.updateLightNavigationBarLw(
-                SYSTEM_UI_FLAG_LIGHT_NAVIGATION_BAR, opaqueLightNavBar, dimming, null, dimming));
-        assertEquals(0, PhoneWindowManager.updateLightNavigationBarLw(
-                SYSTEM_UI_FLAG_LIGHT_NAVIGATION_BAR, opaqueLightNavBar, dimming, imeDrawLightNavBar,
-                dimming));
-
-        // IME window clears SYSTEM_UI_FLAG_LIGHT_NAVIGATION_BAR
-        assertEquals(0, PhoneWindowManager.updateLightNavigationBarLw(
-                SYSTEM_UI_FLAG_LIGHT_NAVIGATION_BAR, null, null, imeDrawDarkNavBar,
-                imeDrawDarkNavBar));
-
-        // Even if the top fullscreen has SYSTEM_UI_FLAG_LIGHT_NAVIGATION_BAR, IME window wins.
-        assertEquals(0, PhoneWindowManager.updateLightNavigationBarLw(
-                SYSTEM_UI_FLAG_LIGHT_NAVIGATION_BAR, opaqueLightNavBar, opaqueLightNavBar,
-                imeDrawDarkNavBar, imeDrawDarkNavBar));
-
-        // IME window should be able to use SYSTEM_UI_FLAG_LIGHT_NAVIGATION_BAR.
-        assertEquals(SYSTEM_UI_FLAG_LIGHT_NAVIGATION_BAR,
-                PhoneWindowManager.updateLightNavigationBarLw(0, opaqueDarkNavBar,
-                        opaqueDarkNavBar, imeDrawLightNavBar, imeDrawLightNavBar));
-    }
-
-    @Test
-    public void testIsDockSideAllowedDockTop() {
-        // Docked top is always allowed
-        assertTrue(PhoneWindowManager.isDockSideAllowed(DOCKED_TOP, DOCKED_LEFT, NAV_BAR_BOTTOM,
-                true /* navigationBarCanMove */));
-        assertTrue(PhoneWindowManager.isDockSideAllowed(DOCKED_TOP, DOCKED_LEFT, NAV_BAR_BOTTOM,
-                false /* navigationBarCanMove */));
-    }
-
-    @Test
-    public void testIsDockSideAllowedDockBottom() {
-        // Cannot dock bottom
-        assertFalse(PhoneWindowManager.isDockSideAllowed(DOCKED_BOTTOM, DOCKED_LEFT, NAV_BAR_BOTTOM,
-                true /* navigationBarCanMove */));
-    }
-
-    @Test
-    public void testIsDockSideAllowedNavigationBarMovable() {
-        assertFalse(PhoneWindowManager.isDockSideAllowed(DOCKED_LEFT, DOCKED_LEFT, NAV_BAR_BOTTOM,
-                true /* navigationBarCanMove */));
-        assertFalse(PhoneWindowManager.isDockSideAllowed(DOCKED_LEFT, DOCKED_LEFT, NAV_BAR_LEFT,
-                true /* navigationBarCanMove */));
-        assertTrue(PhoneWindowManager.isDockSideAllowed(DOCKED_LEFT, DOCKED_LEFT, NAV_BAR_RIGHT,
-                true /* navigationBarCanMove */));
-        assertFalse(PhoneWindowManager.isDockSideAllowed(DOCKED_RIGHT, DOCKED_LEFT, NAV_BAR_BOTTOM,
-                true /* navigationBarCanMove */));
-        assertFalse(PhoneWindowManager.isDockSideAllowed(DOCKED_RIGHT, DOCKED_LEFT, NAV_BAR_RIGHT,
-                true /* navigationBarCanMove */));
-        assertTrue(PhoneWindowManager.isDockSideAllowed(DOCKED_RIGHT, DOCKED_LEFT, NAV_BAR_LEFT,
-                true /* navigationBarCanMove */));
-    }
-
-    @Test
-    public void testIsDockSideAllowedNavigationBarNotMovable() {
-        // Navigation bar is not movable such as tablets
-        assertTrue(PhoneWindowManager.isDockSideAllowed(DOCKED_LEFT, DOCKED_LEFT, NAV_BAR_BOTTOM,
-                false /* navigationBarCanMove */));
-        assertTrue(PhoneWindowManager.isDockSideAllowed(DOCKED_LEFT, DOCKED_TOP, NAV_BAR_BOTTOM,
-                false /* navigationBarCanMove */));
-        assertFalse(PhoneWindowManager.isDockSideAllowed(DOCKED_LEFT, DOCKED_RIGHT, NAV_BAR_BOTTOM,
-                false /* navigationBarCanMove */));
-        assertFalse(PhoneWindowManager.isDockSideAllowed(DOCKED_RIGHT, DOCKED_LEFT, NAV_BAR_BOTTOM,
-                false /* navigationBarCanMove */));
-        assertFalse(PhoneWindowManager.isDockSideAllowed(DOCKED_RIGHT, DOCKED_TOP, NAV_BAR_BOTTOM,
-                false /* navigationBarCanMove */));
-        assertTrue(PhoneWindowManager.isDockSideAllowed(DOCKED_RIGHT, DOCKED_RIGHT, NAV_BAR_BOTTOM,
-                false /* navigationBarCanMove */));
-    }
-}
diff --git a/services/tests/wmtests/src/com/android/server/policy/PhoneWindowManagerTestBase.java b/services/tests/wmtests/src/com/android/server/policy/PhoneWindowManagerTestBase.java
deleted file mode 100644
index 02a33e0..0000000
--- a/services/tests/wmtests/src/com/android/server/policy/PhoneWindowManagerTestBase.java
+++ /dev/null
@@ -1,278 +0,0 @@
-/*
- * Copyright (C) 2017 The Android Open Source Project
- *
- * Licensed under the Apache License, Version 2.0 (the "License");
- * you may not use this file except in compliance with the License.
- * You may obtain a copy of the License at
- *
- *      http://www.apache.org/licenses/LICENSE-2.0
- *
- * Unless required by applicable law or agreed to in writing, software
- * distributed under the License is distributed on an "AS IS" BASIS,
- * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
- * See the License for the specific language governing permissions and
- * limitations under the License.
- */
-
-package com.android.server.policy;
-
-import static android.view.DisplayCutout.BOUNDS_POSITION_BOTTOM;
-import static android.view.DisplayCutout.BOUNDS_POSITION_LEFT;
-import static android.view.DisplayCutout.BOUNDS_POSITION_RIGHT;
-import static android.view.DisplayCutout.BOUNDS_POSITION_TOP;
-import static android.view.Surface.ROTATION_0;
-import static android.view.Surface.ROTATION_180;
-import static android.view.Surface.ROTATION_270;
-import static android.view.Surface.ROTATION_90;
-import static android.view.ViewGroup.LayoutParams.MATCH_PARENT;
-import static android.view.WindowManager.LayoutParams.TYPE_NAVIGATION_BAR;
-import static android.view.WindowManager.LayoutParams.TYPE_STATUS_BAR;
-
-import static androidx.test.platform.app.InstrumentationRegistry.getInstrumentation;
-
-import static com.android.dx.mockito.inline.extended.ExtendedMockito.mock;
-import static com.android.server.wm.utils.CoordinateTransforms
-        .transformPhysicalToLogicalCoordinates;
-
-import static org.junit.Assert.assertEquals;
-
-import android.content.Context;
-import android.content.ContextWrapper;
-import android.content.pm.PackageManager;
-import android.content.res.Resources;
-import android.graphics.Matrix;
-import android.graphics.PixelFormat;
-import android.graphics.Rect;
-import android.graphics.RectF;
-import android.os.IBinder;
-import android.os.UserHandle;
-import android.testing.TestableResources;
-import android.util.Pair;
-import android.view.Display;
-import android.view.DisplayCutout;
-import android.view.DisplayInfo;
-import android.view.Gravity;
-import android.view.View;
-import android.view.WindowManager;
-import android.view.WindowManagerGlobal;
-import android.view.accessibility.AccessibilityManager;
-import android.view.accessibility.IAccessibilityManager;
-
-import com.android.server.policy.keyguard.KeyguardServiceDelegate;
-import com.android.server.wm.DisplayFrames;
-import com.android.server.wm.WindowTestUtils.TestDisplayContent;
-import com.android.server.wm.utils.WmDisplayCutout;
-
-import org.junit.Before;
-
-class PhoneWindowManagerTestBase {
-    static final int DISPLAY_WIDTH = 500;
-    static final int DISPLAY_HEIGHT = 1000;
-
-    static final int STATUS_BAR_HEIGHT = 10;
-    static final int NAV_BAR_HEIGHT = 15;
-    static final int DISPLAY_CUTOUT_HEIGHT = 8;
-
-    TestablePhoneWindowManager mPolicy;
-    TestContextWrapper mContext;
-    DisplayFrames mFrames;
-
-    FakeWindowState mStatusBar;
-    FakeWindowState mNavigationBar;
-    private boolean mHasDisplayCutout;
-    private int mRotation = ROTATION_0;
-
-    @Before
-    public void setUpBase() {
-        mContext = new TestContextWrapper(getInstrumentation().getTargetContext());
-        mContext.getResourceMocker().addOverride(
-                com.android.internal.R.dimen.status_bar_height_portrait, STATUS_BAR_HEIGHT);
-        mContext.getResourceMocker().addOverride(
-                com.android.internal.R.dimen.status_bar_height_landscape, STATUS_BAR_HEIGHT);
-        mContext.getResourceMocker().addOverride(
-                com.android.internal.R.dimen.navigation_bar_height, NAV_BAR_HEIGHT);
-        mContext.getResourceMocker().addOverride(
-                com.android.internal.R.dimen.navigation_bar_height_landscape, NAV_BAR_HEIGHT);
-        mContext.getResourceMocker().addOverride(
-                com.android.internal.R.dimen.navigation_bar_width, NAV_BAR_HEIGHT);
-
-        mPolicy = TestablePhoneWindowManager.create(mContext);
-
-        updateDisplayFrames();
-    }
-
-    public void setRotation(int rotation) {
-        mRotation = rotation;
-        updateDisplayFrames();
-    }
-
-    private void updateDisplayFrames() {
-        Pair<DisplayInfo, WmDisplayCutout> info = displayInfoAndCutoutForRotation(mRotation,
-                mHasDisplayCutout);
-        mFrames = new DisplayFrames(Display.DEFAULT_DISPLAY, info.first, info.second);
-    }
-
-    public void addStatusBar() {
-        mStatusBar = new FakeWindowState();
-        mStatusBar.attrs = new WindowManager.LayoutParams(MATCH_PARENT, STATUS_BAR_HEIGHT,
-                TYPE_STATUS_BAR, 0 /* flags */, PixelFormat.TRANSLUCENT);
-        mStatusBar.attrs.gravity = Gravity.TOP;
-
-        mPolicy.addWindow(mStatusBar);
-        mPolicy.mLastSystemUiFlags |= View.STATUS_BAR_TRANSPARENT;
-    }
-
-    public void addNavigationBar() {
-        mNavigationBar = new FakeWindowState();
-        mNavigationBar.attrs = new WindowManager.LayoutParams(MATCH_PARENT, NAV_BAR_HEIGHT,
-                TYPE_NAVIGATION_BAR, 0 /* flags */, PixelFormat.TRANSLUCENT);
-        mNavigationBar.attrs.gravity = Gravity.BOTTOM;
-
-        mPolicy.addWindow(mNavigationBar);
-        mPolicy.mLastSystemUiFlags |= View.NAVIGATION_BAR_TRANSPARENT;
-    }
-
-    public void addDisplayCutout() {
-        mHasDisplayCutout = true;
-        updateDisplayFrames();
-    }
-
-    /** Asserts that {@code actual} is inset by the given amounts from the full display rect. */
-    public void assertInsetBy(Rect actual, int expectedInsetLeft, int expectedInsetTop,
-            int expectedInsetRight, int expectedInsetBottom) {
-        assertEquals(new Rect(expectedInsetLeft, expectedInsetTop,
-                mFrames.mDisplayWidth - expectedInsetRight,
-                mFrames.mDisplayHeight - expectedInsetBottom), actual);
-    }
-
-    /**
-     * Asserts that {@code actual} is inset by the given amounts from the full display rect.
-     *
-     * Convenience wrapper for when only the top and bottom inset are non-zero.
-     */
-    public void assertInsetByTopBottom(Rect actual, int expectedInsetTop, int expectedInsetBottom) {
-        assertInsetBy(actual, 0, expectedInsetTop, 0, expectedInsetBottom);
-    }
-
-    public static DisplayInfo displayInfoForRotation(int rotation, boolean withDisplayCutout) {
-        return displayInfoAndCutoutForRotation(rotation, withDisplayCutout).first;
-    }
-    public static Pair<DisplayInfo, WmDisplayCutout> displayInfoAndCutoutForRotation(int rotation,
-            boolean withDisplayCutout) {
-        DisplayInfo info = new DisplayInfo();
-        WmDisplayCutout cutout = null;
-
-        final boolean flippedDimensions = rotation == ROTATION_90 || rotation == ROTATION_270;
-        info.logicalWidth = flippedDimensions ? DISPLAY_HEIGHT : DISPLAY_WIDTH;
-        info.logicalHeight = flippedDimensions ? DISPLAY_WIDTH : DISPLAY_HEIGHT;
-        info.rotation = rotation;
-        if (withDisplayCutout) {
-            cutout = WmDisplayCutout.computeSafeInsets(
-                    displayCutoutForRotation(rotation), info.logicalWidth,
-                    info.logicalHeight);
-            info.displayCutout = cutout.getDisplayCutout();
-        } else {
-            info.displayCutout = null;
-        }
-        return Pair.create(info, cutout);
-    }
-
-    private static DisplayCutout displayCutoutForRotation(int rotation) {
-        RectF rectF = new RectF(DISPLAY_WIDTH / 4, 0, DISPLAY_WIDTH * 3 / 4, DISPLAY_CUTOUT_HEIGHT);
-
-        Matrix m = new Matrix();
-        transformPhysicalToLogicalCoordinates(rotation, DISPLAY_WIDTH, DISPLAY_HEIGHT, m);
-        m.mapRect(rectF);
-
-        int pos = -1;
-        switch (rotation) {
-            case ROTATION_0:
-                pos = BOUNDS_POSITION_TOP;
-                break;
-            case ROTATION_90:
-                pos = BOUNDS_POSITION_LEFT;
-                break;
-            case ROTATION_180:
-                pos = BOUNDS_POSITION_BOTTOM;
-                break;
-            case ROTATION_270:
-                pos = BOUNDS_POSITION_RIGHT;
-                break;
-        }
-
-
-        return DisplayCutout.fromBoundingRect((int) rectF.left, (int) rectF.top,
-                (int) rectF.right, (int) rectF.bottom, pos);
-    }
-
-    static class TestContextWrapper extends ContextWrapper {
-        private final TestableResources mResourceMocker;
-
-        TestContextWrapper(Context targetContext) {
-            super(targetContext);
-            mResourceMocker = new TestableResources(targetContext.getResources());
-        }
-
-        @Override
-        public int checkPermission(String permission, int pid, int uid) {
-            return PackageManager.PERMISSION_GRANTED;
-        }
-
-        @Override
-        public int checkPermission(String permission, int pid, int uid, IBinder callerToken) {
-            return PackageManager.PERMISSION_GRANTED;
-        }
-
-        @Override
-        public Resources getResources() {
-            return mResourceMocker.getResources();
-        }
-
-        public TestableResources getResourceMocker() {
-            return mResourceMocker;
-        }
-    }
-
-    static class TestablePhoneWindowManager extends PhoneWindowManager {
-
-        TestablePhoneWindowManager() {
-        }
-
-        @Override
-        void initializeHdmiState() {
-            // Do nothing.
-        }
-
-        @Override
-        Context getSystemUiContext() {
-            return mContext;
-        }
-
-        void addWindow(WindowState state) {
-            if (state instanceof FakeWindowState) {
-                ((FakeWindowState) state).surfaceLayer =
-                        getWindowLayerFromTypeLw(state.getAttrs().type,
-                                true /* canAddInternalSystemWindow */);
-            }
-            adjustWindowParamsLw(state, state.getAttrs(), true /* hasStatusBarPermission */);
-            assertEquals(WindowManagerGlobal.ADD_OKAY, prepareAddWindowLw(state, state.getAttrs()));
-        }
-
-        public static TestablePhoneWindowManager create(Context context) {
-            TestablePhoneWindowManager[] policy = new TestablePhoneWindowManager[1];
-            getInstrumentation().runOnMainSync(() -> {
-                policy[0] = new TestablePhoneWindowManager();
-                policy[0].mContext = context;
-                policy[0].mKeyguardDelegate = mock(KeyguardServiceDelegate.class);
-                policy[0].mAccessibilityManager = new AccessibilityManager(context,
-                        mock(IAccessibilityManager.class), UserHandle.USER_CURRENT);
-                policy[0].mSystemGestures = mock(SystemGesturesPointerEventListener.class);
-
-                final TestDisplayContent displayContent = TestDisplayContent.create(context);
-                policy[0].setDefaultDisplay(displayContent);
-                policy[0].onConfigurationChanged(displayContent);
-            });
-            return policy[0];
-        }
-    }
-}
diff --git a/services/tests/wmtests/src/com/android/server/wm/ActivityRecordTests.java b/services/tests/wmtests/src/com/android/server/wm/ActivityRecordTests.java
index 6ed83de..170bd33 100644
--- a/services/tests/wmtests/src/com/android/server/wm/ActivityRecordTests.java
+++ b/services/tests/wmtests/src/com/android/server/wm/ActivityRecordTests.java
@@ -163,7 +163,8 @@
     private void verifyPositionWithLimitedAspectRatio(int navBarPosition, Rect taskBounds,
             float aspectRatio, Rect expectedActivityBounds) {
         // Verify with nav bar on the right.
-        when(mService.mWindowManager.getNavBarPosition()).thenReturn(navBarPosition);
+        when(mService.mWindowManager.getNavBarPosition(mActivity.getDisplayId()))
+                .thenReturn(navBarPosition);
         mTask.getConfiguration().windowConfiguration.setAppBounds(taskBounds);
         mActivity.info.maxAspectRatio = aspectRatio;
         mActivity.ensureActivityConfiguration(
