blob: 5b0c4711ef28ceea1d2c3602df7ba93f3bb587c8 [file] [log] [blame]
Wale Ogunwalee05f5012016-09-16 16:27:29 -07001/*
2 * Copyright (C) 2016 The Android Open Source Project
3 *
4 * Licensed under the Apache License, Version 2.0 (the "License");
5 * you may not use this file except in compliance with the License.
6 * You may obtain a copy of the License at
7 *
8 * http://www.apache.org/licenses/LICENSE-2.0
9 *
10 * Unless required by applicable law or agreed to in writing, software
11 * distributed under the License is distributed on an "AS IS" BASIS,
12 * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
13 * See the License for the specific language governing permissions and
14 * limitations under the License
15 */
16
17package com.android.server.wm;
18
19import android.app.AppOpsManager;
20import android.content.res.Configuration;
21import android.graphics.Rect;
22import android.os.Binder;
23import android.os.Debug;
24import android.os.ParcelFileDescriptor;
25import android.os.PowerManager;
26import android.os.RemoteException;
27import android.os.SystemClock;
28import android.os.UserHandle;
29import android.provider.Settings;
30import android.util.EventLog;
31import android.util.Slog;
Wale Ogunwalee05f5012016-09-16 16:27:29 -070032import android.util.SparseIntArray;
33import android.view.Display;
34import android.view.DisplayInfo;
35import android.view.InputChannel;
36import android.view.WindowManager;
37import com.android.internal.util.ArrayUtils;
38import com.android.server.EventLogTags;
39import com.android.server.input.InputWindowHandle;
40
41import java.io.FileDescriptor;
42import java.io.PrintWriter;
43import java.util.ArrayList;
44
45import static android.app.ActivityManager.StackId.DOCKED_STACK_ID;
46import static android.view.WindowManager.LayoutParams.FLAG_KEEP_SCREEN_ON;
47import static android.view.WindowManager.LayoutParams.FLAG_SHOW_WALLPAPER;
48import static android.view.WindowManager.LayoutParams.PRIVATE_FLAG_KEYGUARD;
49import static android.view.WindowManager.LayoutParams.PRIVATE_FLAG_NO_MOVE_ANIMATION;
50import static android.view.WindowManager.LayoutParams.PRIVATE_FLAG_SUSTAINED_PERFORMANCE_MODE;
51import static android.view.WindowManager.LayoutParams.TYPE_DREAM;
52import static android.view.WindowManager.LayoutParams.TYPE_KEYGUARD_DIALOG;
53import static android.view.WindowManager.LayoutParams.TYPE_SYSTEM_DIALOG;
54import static android.view.WindowManager.LayoutParams.TYPE_SYSTEM_ERROR;
55import static android.view.WindowManagerPolicy.FINISH_LAYOUT_REDO_ANIM;
56import static android.view.WindowManagerPolicy.FINISH_LAYOUT_REDO_CONFIG;
57import static android.view.WindowManagerPolicy.FINISH_LAYOUT_REDO_LAYOUT;
58import static android.view.WindowManagerPolicy.FINISH_LAYOUT_REDO_WALLPAPER;
59import static android.view.WindowManager.LayoutParams.TYPE_WALLPAPER;
60import static com.android.server.wm.WindowManagerDebugConfig.DEBUG_ADD_REMOVE;
61import static com.android.server.wm.WindowManagerDebugConfig.DEBUG_DISPLAY;
62import static com.android.server.wm.WindowManagerDebugConfig.DEBUG_KEEP_SCREEN_ON;
63import static com.android.server.wm.WindowManagerDebugConfig.DEBUG_LAYOUT;
64import static com.android.server.wm.WindowManagerDebugConfig.DEBUG_LAYOUT_REPEATS;
65import static com.android.server.wm.WindowManagerDebugConfig.DEBUG_ORIENTATION;
66import static com.android.server.wm.WindowManagerDebugConfig.DEBUG_POWER;
67import static com.android.server.wm.WindowManagerDebugConfig.DEBUG_STACK;
68import static com.android.server.wm.WindowManagerDebugConfig.DEBUG_STARTING_WINDOW;
69import static com.android.server.wm.WindowManagerDebugConfig.DEBUG_TOKEN_MOVEMENT;
70import static com.android.server.wm.WindowManagerDebugConfig.DEBUG_VISIBILITY;
71import static com.android.server.wm.WindowManagerDebugConfig.DEBUG_WALLPAPER_LIGHT;
72import static com.android.server.wm.WindowManagerDebugConfig.DEBUG_WINDOW_TRACE;
73import static com.android.server.wm.WindowManagerDebugConfig.SHOW_LIGHT_TRANSACTIONS;
74import static com.android.server.wm.WindowManagerDebugConfig.SHOW_SURFACE_ALLOC;
75import static com.android.server.wm.WindowManagerDebugConfig.SHOW_TRANSACTIONS;
76import static com.android.server.wm.WindowManagerDebugConfig.TAG_KEEP_SCREEN_ON;
77import static com.android.server.wm.WindowManagerDebugConfig.TAG_WITH_CLASS_NAME;
78import static com.android.server.wm.WindowManagerDebugConfig.TAG_WM;
79import static com.android.server.wm.WindowManagerService.H.NOTIFY_STARTING_WINDOW_DRAWN;
80import static com.android.server.wm.WindowManagerService.H.REPORT_LOSING_FOCUS;
81import static com.android.server.wm.WindowManagerService.H.SEND_NEW_CONFIGURATION;
82import static com.android.server.wm.WindowManagerService.LAYOUT_REPEAT_THRESHOLD;
83import static com.android.server.wm.WindowManagerService.UPDATE_FOCUS_PLACING_SURFACES;
84import static com.android.server.wm.WindowManagerService.UPDATE_FOCUS_WILL_PLACE_SURFACES;
85import static com.android.server.wm.WindowManagerService.WINDOWS_FREEZING_SCREENS_NONE;
86import static com.android.server.wm.WindowManagerService.H.WINDOW_FREEZE_TIMEOUT;
87import static com.android.server.wm.WindowManagerService.logSurface;
88import static com.android.server.wm.WindowSurfacePlacer.SET_FORCE_HIDING_CHANGED;
89import static com.android.server.wm.WindowSurfacePlacer.SET_ORIENTATION_CHANGE_COMPLETE;
90import static com.android.server.wm.WindowSurfacePlacer.SET_TURN_ON_SCREEN;
91import static com.android.server.wm.WindowSurfacePlacer.SET_UPDATE_ROTATION;
92import static com.android.server.wm.WindowSurfacePlacer.SET_WALLPAPER_ACTION_PENDING;
93import static com.android.server.wm.WindowSurfacePlacer.SET_WALLPAPER_MAY_CHANGE;
94
95/** Root {@link WindowContainer} for the device. */
96// TODO: Several methods in here are accessing children of this container's children through various
97// references (WindowList I am looking at you :/). See if we can delegate instead.
Wale Ogunwaleeaabfab2016-09-16 17:19:52 -070098class RootWindowContainer extends WindowContainer<DisplayContent> {
Wale Ogunwalee05f5012016-09-16 16:27:29 -070099 private static final String TAG = TAG_WITH_CLASS_NAME ? "RootWindowContainer" : TAG_WM;
100
101 WindowManagerService mService;
102
Wale Ogunwalee05f5012016-09-16 16:27:29 -0700103 private boolean mWallpaperForceHidingChanged = false;
104 private Object mLastWindowFreezeSource = null;
105 private Session mHoldScreen = null;
106 private float mScreenBrightness = -1;
107 private float mButtonBrightness = -1;
108 private long mUserActivityTimeout = -1;
109 private boolean mUpdateRotation = false;
110 private boolean mObscured = false;
111 boolean mSyswin = false;
112 // Set to true when the display contains content to show the user.
113 // When false, the display manager may choose to mirror or blank the display.
114 private boolean mDisplayHasContent = false;
115 private float mPreferredRefreshRate = 0;
116 private int mPreferredModeId = 0;
117 // Following variables are for debugging screen wakelock only.
118 // Last window that requires screen wakelock
119 WindowState mHoldScreenWindow = null;
120 // Last window that obscures all windows below
121 WindowState mObsuringWindow = null;
122 // Only set while traversing the default display based on its content.
123 // Affects the behavior of mirroring on secondary displays.
124 private boolean mObscureApplicationContentOnSecondaryDisplays = false;
125
126 private boolean mSustainedPerformanceModeEnabled = false;
127 private boolean mSustainedPerformanceModeCurrent = false;
128
129 boolean mWallpaperMayChange = false;
Robert Carr11c26c22016-09-23 12:40:27 -0700130 // During an orientation change, we track whether all windows have rendered
131 // at the new orientation, and this will be false from changing orientation until that occurs.
132 // For seamless rotation cases this always stays true, as the windows complete their orientation
133 // changes 1 by 1 without disturbing global state.
Wale Ogunwalee05f5012016-09-16 16:27:29 -0700134 boolean mOrientationChangeComplete = true;
135 boolean mWallpaperActionPending = false;
136
137 private final ArrayList<Integer> mChangedStackList = new ArrayList();
138
139 // State for the RemoteSurfaceTrace system used in testing. If this is enabled SurfaceControl
140 // instances will be replaced with an instance that writes a binary representation of all
141 // commands to mSurfaceTraceFd.
142 boolean mSurfaceTraceEnabled;
143 ParcelFileDescriptor mSurfaceTraceFd;
144 RemoteEventTrace mRemoteEventTrace;
145
146 RootWindowContainer(WindowManagerService service) {
147 mService = service;
148 }
149
150 WindowState computeFocusedWindow() {
Wale Ogunwaleeaabfab2016-09-16 17:19:52 -0700151 final int count = mChildren.size();
Wale Ogunwalee05f5012016-09-16 16:27:29 -0700152 for (int i = 0; i < count; i++) {
Wale Ogunwaleeaabfab2016-09-16 17:19:52 -0700153 final DisplayContent dc = mChildren.get(i);
Wale Ogunwalee05f5012016-09-16 16:27:29 -0700154 final WindowState win = dc.findFocusedWindow();
155 if (win != null) {
156 return win;
157 }
158 }
159 return null;
160 }
161
162 /**
163 * Retrieve the DisplayContent for the specified displayId. Will create a new DisplayContent if
164 * there is a Display for the displayId.
165 *
166 * @param displayId The display the caller is interested in.
167 * @return The DisplayContent associated with displayId or null if there is no Display for it.
168 */
Wale Ogunwaleeaabfab2016-09-16 17:19:52 -0700169 DisplayContent getDisplayContentOrCreate(int displayId) {
170 DisplayContent dc = getDisplayContent(displayId);
171
Wale Ogunwalee05f5012016-09-16 16:27:29 -0700172 if (dc == null) {
173 final Display display = mService.mDisplayManager.getDisplay(displayId);
174 if (display != null) {
175 dc = createDisplayContent(display);
176 }
177 }
178 return dc;
179 }
180
Wale Ogunwaleeaabfab2016-09-16 17:19:52 -0700181 private DisplayContent getDisplayContent(int displayId) {
182 for (int i = mChildren.size() - 1; i >= 0; --i) {
183 final DisplayContent current = mChildren.get(i);
184 if (current.getDisplayId() == displayId) {
185 return current;
186 }
187 }
188 return null;
189 }
Wale Ogunwalee05f5012016-09-16 16:27:29 -0700190
Wale Ogunwaleeaabfab2016-09-16 17:19:52 -0700191 private DisplayContent createDisplayContent(final Display display) {
192 final DisplayContent dc = new DisplayContent(display, mService);
193 final int displayId = display.getDisplayId();
194
195 if (DEBUG_DISPLAY) Slog.v(TAG_WM, "Adding display=" + display);
196 addChild(dc, null);
197
198 final DisplayInfo displayInfo = dc.getDisplayInfo();
Wale Ogunwalee05f5012016-09-16 16:27:29 -0700199 final Rect rect = new Rect();
200 mService.mDisplaySettings.getOverscanLocked(displayInfo.name, displayInfo.uniqueId, rect);
201 displayInfo.overscanLeft = rect.left;
202 displayInfo.overscanTop = rect.top;
203 displayInfo.overscanRight = rect.right;
204 displayInfo.overscanBottom = rect.bottom;
205 if (mService.mDisplayManagerInternal != null) {
206 mService.mDisplayManagerInternal.setDisplayInfoOverrideFromWindowManager(
207 displayId, displayInfo);
Wale Ogunwaleeaabfab2016-09-16 17:19:52 -0700208 mService.configureDisplayPolicyLocked(dc);
Wale Ogunwalee05f5012016-09-16 16:27:29 -0700209
210 // TODO(multi-display): Create an input channel for each display with touch capability.
211 if (displayId == Display.DEFAULT_DISPLAY) {
Wale Ogunwaleeaabfab2016-09-16 17:19:52 -0700212 dc.mTapDetector = new TaskTapPointerEventListener(
213 mService, dc);
214 mService.registerPointerEventListener(dc.mTapDetector);
Wale Ogunwalee05f5012016-09-16 16:27:29 -0700215 mService.registerPointerEventListener(mService.mMousePositionTracker);
216 }
217 }
218
Wale Ogunwaleeaabfab2016-09-16 17:19:52 -0700219 return dc;
Wale Ogunwalee05f5012016-09-16 16:27:29 -0700220 }
221
222 /** Adds the input stack id to the input display id and returns the bounds of the added stack.*/
223 Rect addStackToDisplay(int stackId, int displayId, boolean onTop) {
Wale Ogunwaleeaabfab2016-09-16 17:19:52 -0700224 final DisplayContent dc = getDisplayContent(displayId);
Wale Ogunwalee05f5012016-09-16 16:27:29 -0700225 if (dc == null) {
226 Slog.w(TAG_WM, "addStackToDisplay: Trying to add stackId=" + stackId
227 + " to unknown displayId=" + displayId + " callers=" + Debug.getCallers(6));
228 return null;
229 }
230
231 boolean attachedToDisplay = false;
232 TaskStack stack = mService.mStackIdToStack.get(stackId);
233 if (stack == null) {
234 if (DEBUG_STACK) Slog.d(TAG_WM, "attachStack: stackId=" + stackId);
235
236 stack = dc.getStackById(stackId);
237 if (stack != null) {
Wale Ogunwaleba51ca22016-09-23 06:06:54 -0700238 // It's already attached to the display...clear mDeferRemoval and move stack to
239 // appropriate z-order on display as needed.
Wale Ogunwalee05f5012016-09-16 16:27:29 -0700240 stack.mDeferRemoval = false;
Wale Ogunwaleba51ca22016-09-23 06:06:54 -0700241 dc.moveStack(stack, onTop);
Wale Ogunwalee05f5012016-09-16 16:27:29 -0700242 attachedToDisplay = true;
243 } else {
244 stack = new TaskStack(mService, stackId);
245 }
246
247 mService.mStackIdToStack.put(stackId, stack);
248 if (stackId == DOCKED_STACK_ID) {
249 mService.getDefaultDisplayContentLocked().mDividerControllerLocked
250 .notifyDockedStackExistsChanged(true);
251 }
252 }
Wale Ogunwaleba51ca22016-09-23 06:06:54 -0700253
Wale Ogunwalee05f5012016-09-16 16:27:29 -0700254 if (!attachedToDisplay) {
255 stack.attachDisplayContent(dc);
Wale Ogunwaleba51ca22016-09-23 06:06:54 -0700256 dc.attachStack(stack, onTop);
Wale Ogunwalee05f5012016-09-16 16:27:29 -0700257 }
Wale Ogunwaleba51ca22016-09-23 06:06:54 -0700258
Wale Ogunwalee05f5012016-09-16 16:27:29 -0700259 if (stack.getRawFullscreen()) {
260 return null;
261 }
Wale Ogunwaleba51ca22016-09-23 06:06:54 -0700262 final Rect bounds = new Rect();
Wale Ogunwalee05f5012016-09-16 16:27:29 -0700263 stack.getRawBounds(bounds);
264 return bounds;
265 }
266
Wale Ogunwale2b06bfc2016-09-28 14:17:05 -0700267 boolean isLayoutNeeded() {
Wale Ogunwaleeaabfab2016-09-16 17:19:52 -0700268 final int numDisplays = mChildren.size();
Wale Ogunwalee05f5012016-09-16 16:27:29 -0700269 for (int displayNdx = 0; displayNdx < numDisplays; ++displayNdx) {
Wale Ogunwaleeaabfab2016-09-16 17:19:52 -0700270 final DisplayContent displayContent = mChildren.get(displayNdx);
Wale Ogunwale2b06bfc2016-09-28 14:17:05 -0700271 if (displayContent.isLayoutNeeded()) {
Wale Ogunwalee05f5012016-09-16 16:27:29 -0700272 return true;
273 }
274 }
275 return false;
276 }
277
278 void getWindows(WindowList output) {
Wale Ogunwaleeaabfab2016-09-16 17:19:52 -0700279 final int count = mChildren.size();
Wale Ogunwalee05f5012016-09-16 16:27:29 -0700280 for (int i = 0; i < count; ++i) {
Wale Ogunwaleeaabfab2016-09-16 17:19:52 -0700281 final DisplayContent dc = mChildren.get(i);
Wale Ogunwalee05f5012016-09-16 16:27:29 -0700282 output.addAll(dc.getWindowList());
283 }
284 }
285
286 void getWindows(WindowList output, boolean visibleOnly, boolean appsOnly) {
Wale Ogunwaleeaabfab2016-09-16 17:19:52 -0700287 final int numDisplays = mChildren.size();
Wale Ogunwalee05f5012016-09-16 16:27:29 -0700288 for (int displayNdx = 0; displayNdx < numDisplays; ++displayNdx) {
Wale Ogunwaleeaabfab2016-09-16 17:19:52 -0700289 final WindowList windowList = mChildren.get(displayNdx).getWindowList();
Wale Ogunwalee05f5012016-09-16 16:27:29 -0700290 for (int winNdx = windowList.size() - 1; winNdx >= 0; --winNdx) {
291 final WindowState w = windowList.get(winNdx);
292 if ((!visibleOnly || w.mWinAnimator.getShown())
293 && (!appsOnly || w.mAppToken != null)) {
294 output.add(w);
295 }
296 }
297 }
298 }
299
300 void getWindowsByName(WindowList output, String name) {
301 int objectId = 0;
302 // See if this is an object ID.
303 try {
304 objectId = Integer.parseInt(name, 16);
305 name = null;
306 } catch (RuntimeException e) {
307 }
Wale Ogunwaleeaabfab2016-09-16 17:19:52 -0700308 final int numDisplays = mChildren.size();
Wale Ogunwalee05f5012016-09-16 16:27:29 -0700309 for (int displayNdx = 0; displayNdx < numDisplays; ++displayNdx) {
Wale Ogunwaleeaabfab2016-09-16 17:19:52 -0700310 final WindowList windowList = mChildren.get(displayNdx).getWindowList();
Wale Ogunwalee05f5012016-09-16 16:27:29 -0700311 for (int winNdx = windowList.size() - 1; winNdx >= 0; --winNdx) {
312 final WindowState w = windowList.get(winNdx);
313 if (name != null) {
314 if (w.mAttrs.getTitle().toString().contains(name)) {
315 output.add(w);
316 }
317 } else if (System.identityHashCode(w) == objectId) {
318 output.add(w);
319 }
320 }
321 }
322 }
323
324 WindowState findWindow(int hashCode) {
Wale Ogunwaleeaabfab2016-09-16 17:19:52 -0700325 final int numDisplays = mChildren.size();
Wale Ogunwalee05f5012016-09-16 16:27:29 -0700326 for (int displayNdx = 0; displayNdx < numDisplays; ++displayNdx) {
Wale Ogunwaleeaabfab2016-09-16 17:19:52 -0700327 final WindowList windows = mChildren.get(displayNdx).getWindowList();
Wale Ogunwalee05f5012016-09-16 16:27:29 -0700328 final int numWindows = windows.size();
329 for (int winNdx = 0; winNdx < numWindows; ++winNdx) {
330 final WindowState w = windows.get(winNdx);
331 if (System.identityHashCode(w) == hashCode) {
332 return w;
333 }
334 }
335 }
336
337 return null;
338 }
339
340 // TODO: Users would have their own window containers under the display container?
341 void switchUser() {
Wale Ogunwaleeaabfab2016-09-16 17:19:52 -0700342 final int count = mChildren.size();
Wale Ogunwalee05f5012016-09-16 16:27:29 -0700343 for (int i = 0; i < count; ++i) {
Wale Ogunwaleeaabfab2016-09-16 17:19:52 -0700344 final DisplayContent dc = mChildren.get(i);
Wale Ogunwalee05f5012016-09-16 16:27:29 -0700345 dc.switchUser();
346 }
347 }
348
349 int[] onConfigurationChanged(Configuration config) {
350 prepareFreezingTaskBounds();
351 mService.mGlobalConfiguration = new Configuration(config);
352
353 mService.mPolicy.onConfigurationChanged();
354
355 mChangedStackList.clear();
356
Wale Ogunwaleeaabfab2016-09-16 17:19:52 -0700357 final int numDisplays = mChildren.size();
358 for (int i = 0; i < numDisplays; ++i) {
359 final DisplayContent dc = mChildren.get(i);
360 dc.onConfigurationChanged(mChangedStackList);
Wale Ogunwalee05f5012016-09-16 16:27:29 -0700361 }
362
363 return mChangedStackList.isEmpty() ? null : ArrayUtils.convertToIntArray(mChangedStackList);
364 }
365
366 private void prepareFreezingTaskBounds() {
Wale Ogunwaleeaabfab2016-09-16 17:19:52 -0700367 for (int i = mChildren.size() - 1; i >= 0; i--) {
368 mChildren.get(i).prepareFreezingTaskBounds();
Wale Ogunwalee05f5012016-09-16 16:27:29 -0700369 }
370 }
371
372 void setSecureSurfaceState(int userId, boolean disabled) {
Wale Ogunwaleeaabfab2016-09-16 17:19:52 -0700373 for (int i = mChildren.size() - 1; i >= 0; --i) {
374 final WindowList windows = mChildren.get(i).getWindowList();
Wale Ogunwalee05f5012016-09-16 16:27:29 -0700375 for (int winNdx = windows.size() - 1; winNdx >= 0; --winNdx) {
376 final WindowState win = windows.get(winNdx);
377 if (win.mHasSurface && userId == UserHandle.getUserId(win.mOwnerUid)) {
378 win.mWinAnimator.setSecureLocked(disabled);
379 }
380 }
381 }
382 }
383
384 void updateAppOpsState() {
Wale Ogunwaleeaabfab2016-09-16 17:19:52 -0700385 final int count = mChildren.size();
Wale Ogunwalee05f5012016-09-16 16:27:29 -0700386 for (int i = 0; i < count; ++i) {
Wale Ogunwaleeaabfab2016-09-16 17:19:52 -0700387 final WindowList windows = mChildren.get(i).getWindowList();
Wale Ogunwalee05f5012016-09-16 16:27:29 -0700388 final int numWindows = windows.size();
389 for (int winNdx = 0; winNdx < numWindows; ++winNdx) {
390 final WindowState win = windows.get(winNdx);
391 if (win.mAppOp == AppOpsManager.OP_NONE) {
392 continue;
393 }
394 final int mode = mService.mAppOps.checkOpNoThrow(win.mAppOp, win.getOwningUid(),
395 win.getOwningPackage());
396 win.setAppOpVisibilityLw(mode == AppOpsManager.MODE_ALLOWED ||
397 mode == AppOpsManager.MODE_DEFAULT);
398 }
399 }
400 }
401
402 boolean canShowStrictModeViolation(int pid) {
Wale Ogunwaleeaabfab2016-09-16 17:19:52 -0700403 final int count = mChildren.size();
Wale Ogunwalee05f5012016-09-16 16:27:29 -0700404 for (int i = 0; i < count; ++i) {
Wale Ogunwaleeaabfab2016-09-16 17:19:52 -0700405 final WindowList windows = mChildren.get(i).getWindowList();
Wale Ogunwalee05f5012016-09-16 16:27:29 -0700406 final int numWindows = windows.size();
407 for (int winNdx = 0; winNdx < numWindows; ++winNdx) {
408 final WindowState ws = windows.get(winNdx);
409 if (ws.mSession.mPid == pid && ws.isVisibleLw()) {
410 return true;
411 }
412 }
413 }
414 return false;
415 }
416
417 void closeSystemDialogs(String reason) {
Wale Ogunwaleeaabfab2016-09-16 17:19:52 -0700418 final int count = mChildren.size();
Wale Ogunwalee05f5012016-09-16 16:27:29 -0700419 for (int i = 0; i < count; ++i) {
Wale Ogunwaleeaabfab2016-09-16 17:19:52 -0700420 final WindowList windows = mChildren.get(i).getWindowList();
Wale Ogunwalee05f5012016-09-16 16:27:29 -0700421 final int numWindows = windows.size();
422 for (int j = 0; j < numWindows; ++j) {
423 final WindowState w = windows.get(j);
424 if (w.mHasSurface) {
425 try {
426 w.mClient.closeSystemDialogs(reason);
427 } catch (RemoteException e) {
428 }
429 }
430 }
431 }
432 }
433
434 void removeReplacedWindows() {
435 if (SHOW_TRANSACTIONS) Slog.i(TAG, ">>> OPEN TRANSACTION removeReplacedWindows");
436 mService.openSurfaceTransaction();
437 try {
Wale Ogunwaleeaabfab2016-09-16 17:19:52 -0700438 for (int i = mChildren.size() - 1; i >= 0; i--) {
439 DisplayContent dc = mChildren.get(i);
Wale Ogunwalee05f5012016-09-16 16:27:29 -0700440 final WindowList windows = dc.getWindowList();
441 for (int j = windows.size() - 1; j >= 0; j--) {
442 final WindowState win = windows.get(j);
443 final AppWindowToken aToken = win.mAppToken;
444 if (aToken != null) {
445 aToken.removeReplacedWindowIfNeeded(win);
446 }
447 }
448 }
449 } finally {
450 mService.closeSurfaceTransaction();
451 if (SHOW_TRANSACTIONS) Slog.i(TAG, "<<< CLOSE TRANSACTION removeReplacedWindows");
452 }
453 }
454
455 boolean hasPendingLayoutChanges(WindowAnimator animator) {
456 boolean hasChanges = false;
457
Wale Ogunwaleeaabfab2016-09-16 17:19:52 -0700458 final int count = mChildren.size();
Wale Ogunwalee05f5012016-09-16 16:27:29 -0700459 for (int i = 0; i < count; ++i) {
Wale Ogunwaleeaabfab2016-09-16 17:19:52 -0700460 final DisplayContent dc = mChildren.get(i);
Wale Ogunwalee05f5012016-09-16 16:27:29 -0700461 final int pendingChanges = animator.getPendingLayoutChanges(dc.getDisplayId());
462 if ((pendingChanges & FINISH_LAYOUT_REDO_WALLPAPER) != 0) {
463 animator.mBulkUpdateParams |= SET_WALLPAPER_ACTION_PENDING;
464 }
465 if (pendingChanges != 0) {
466 hasChanges = true;
467 }
468 }
469
470 return hasChanges;
471 }
472
473 void updateInputWindows(InputMonitor inputMonitor, WindowState inputFocus, boolean inDrag) {
474 boolean addInputConsumerHandle = mService.mInputConsumer != null;
475 boolean addWallpaperInputConsumerHandle = mService.mWallpaperInputConsumer != null;
476 final WallpaperController wallpaperController = mService.mWallpaperControllerLocked;
477 boolean disableWallpaperTouchEvents = false;
478
Wale Ogunwaleeaabfab2016-09-16 17:19:52 -0700479 final int count = mChildren.size();
Wale Ogunwalee05f5012016-09-16 16:27:29 -0700480 for (int i = 0; i < count; ++i) {
Wale Ogunwaleeaabfab2016-09-16 17:19:52 -0700481 final DisplayContent dc = mChildren.get(i);
Wale Ogunwalee05f5012016-09-16 16:27:29 -0700482 final WindowList windows = dc.getWindowList();
483 for (int winNdx = windows.size() - 1; winNdx >= 0; --winNdx) {
484 final WindowState child = windows.get(winNdx);
485 final InputChannel inputChannel = child.mInputChannel;
486 final InputWindowHandle inputWindowHandle = child.mInputWindowHandle;
487 if (inputChannel == null || inputWindowHandle == null || child.mRemoved
488 || child.isAdjustedForMinimizedDock()) {
489 // Skip this window because it cannot possibly receive input.
490 continue;
491 }
492 if (addInputConsumerHandle
493 && inputWindowHandle.layer <= mService.mInputConsumer.mWindowHandle.layer) {
494 inputMonitor.addInputWindowHandle(mService.mInputConsumer.mWindowHandle);
495 addInputConsumerHandle = false;
496 }
497
498 if (addWallpaperInputConsumerHandle) {
499 if (child.mAttrs.type == WindowManager.LayoutParams.TYPE_WALLPAPER &&
500 child.isVisibleLw()) {
501 // Add the wallpaper input consumer above the first visible wallpaper.
502 inputMonitor.addInputWindowHandle(
503 mService.mWallpaperInputConsumer.mWindowHandle);
504 addWallpaperInputConsumerHandle = false;
505 }
506 }
507
508 final int flags = child.mAttrs.flags;
509 final int privateFlags = child.mAttrs.privateFlags;
510 final int type = child.mAttrs.type;
511
512 final boolean hasFocus = child == inputFocus;
513 final boolean isVisible = child.isVisibleLw();
514 if ((privateFlags
515 & WindowManager.LayoutParams.PRIVATE_FLAG_DISABLE_WALLPAPER_TOUCH_EVENTS)
516 != 0) {
517 disableWallpaperTouchEvents = true;
518 }
519 final boolean hasWallpaper = wallpaperController.isWallpaperTarget(child)
520 && (privateFlags & WindowManager.LayoutParams.PRIVATE_FLAG_KEYGUARD) == 0
521 && !disableWallpaperTouchEvents;
522 final boolean onDefaultDisplay = (child.getDisplayId() == Display.DEFAULT_DISPLAY);
523
524 // If there's a drag in progress and 'child' is a potential drop target,
525 // make sure it's been told about the drag
526 if (inDrag && isVisible && onDefaultDisplay) {
527 mService.mDragState.sendDragStartedIfNeededLw(child);
528 }
529
530 inputMonitor.addInputWindowHandle(
531 inputWindowHandle, child, flags, type, isVisible, hasFocus, hasWallpaper);
532 }
533 }
534
535 if (addWallpaperInputConsumerHandle) {
536 // No visible wallpaper found, add the wallpaper input consumer at the end.
537 inputMonitor.addInputWindowHandle(mService.mWallpaperInputConsumer.mWindowHandle);
538 }
539 }
540
541 boolean reclaimSomeSurfaceMemory(WindowStateAnimator winAnimator, String operation,
542 boolean secure) {
543 final WindowSurfaceController surfaceController = winAnimator.mSurfaceController;
544 boolean leakedSurface = false;
545 boolean killedApps = false;
546
547 EventLog.writeEvent(EventLogTags.WM_NO_SURFACE_MEMORY, winAnimator.mWin.toString(),
548 winAnimator.mSession.mPid, operation);
549
550 final long callingIdentity = Binder.clearCallingIdentity();
551 try {
552 // There was some problem... first, do a sanity check of the window list to make sure
553 // we haven't left any dangling surfaces around.
554
555 Slog.i(TAG_WM, "Out of memory for surface! Looking for leaks...");
Wale Ogunwaleeaabfab2016-09-16 17:19:52 -0700556 final int numDisplays = mChildren.size();
Wale Ogunwalee05f5012016-09-16 16:27:29 -0700557 for (int displayNdx = 0; displayNdx < numDisplays; ++displayNdx) {
Wale Ogunwaleeaabfab2016-09-16 17:19:52 -0700558 final WindowList windows = mChildren.get(displayNdx).getWindowList();
Wale Ogunwalee05f5012016-09-16 16:27:29 -0700559 final int numWindows = windows.size();
560 for (int winNdx = 0; winNdx < numWindows; ++winNdx) {
561 final WindowState ws = windows.get(winNdx);
562 final WindowStateAnimator wsa = ws.mWinAnimator;
563 if (wsa.mSurfaceController == null) {
564 continue;
565 }
566 if (!mService.mSessions.contains(wsa.mSession)) {
567 Slog.w(TAG_WM, "LEAKED SURFACE (session doesn't exist): "
568 + ws + " surface=" + wsa.mSurfaceController
569 + " token=" + ws.mToken
570 + " pid=" + ws.mSession.mPid
571 + " uid=" + ws.mSession.mUid);
572 wsa.destroySurface();
573 mService.mForceRemoves.add(ws);
574 leakedSurface = true;
575 } else if (ws.mAppToken != null && ws.mAppToken.clientHidden) {
576 Slog.w(TAG_WM, "LEAKED SURFACE (app token hidden): "
577 + ws + " surface=" + wsa.mSurfaceController
578 + " token=" + ws.mAppToken
579 + " saved=" + ws.hasSavedSurface());
580 if (SHOW_TRANSACTIONS) logSurface(ws, "LEAK DESTROY", false);
581 wsa.destroySurface();
582 leakedSurface = true;
583 }
584 }
585 }
586
587 if (!leakedSurface) {
588 Slog.w(TAG_WM, "No leaked surfaces; killing applications!");
589 SparseIntArray pidCandidates = new SparseIntArray();
590 for (int displayNdx = 0; displayNdx < numDisplays; ++displayNdx) {
Wale Ogunwaleeaabfab2016-09-16 17:19:52 -0700591 final WindowList windows = mChildren.get(displayNdx).getWindowList();
Wale Ogunwalee05f5012016-09-16 16:27:29 -0700592 final int numWindows = windows.size();
593 for (int winNdx = 0; winNdx < numWindows; ++winNdx) {
594 final WindowState ws = windows.get(winNdx);
595 if (mService.mForceRemoves.contains(ws)) {
596 continue;
597 }
598 WindowStateAnimator wsa = ws.mWinAnimator;
599 if (wsa.mSurfaceController != null) {
600 pidCandidates.append(wsa.mSession.mPid, wsa.mSession.mPid);
601 }
602 }
603 if (pidCandidates.size() > 0) {
604 int[] pids = new int[pidCandidates.size()];
605 for (int i = 0; i < pids.length; i++) {
606 pids[i] = pidCandidates.keyAt(i);
607 }
608 try {
609 if (mService.mActivityManager.killPids(pids, "Free memory", secure)) {
610 killedApps = true;
611 }
612 } catch (RemoteException e) {
613 }
614 }
615 }
616 }
617
618 if (leakedSurface || killedApps) {
619 // We managed to reclaim some memory, so get rid of the trouble surface and ask the
620 // app to request another one.
621 Slog.w(TAG_WM,
622 "Looks like we have reclaimed some memory, clearing surface for retry.");
623 if (surfaceController != null) {
624 if (SHOW_TRANSACTIONS || SHOW_SURFACE_ALLOC) logSurface(winAnimator.mWin,
625 "RECOVER DESTROY", false);
626 winAnimator.destroySurface();
627 mService.scheduleRemoveStartingWindowLocked(winAnimator.mWin.mAppToken);
628 }
629
630 try {
631 winAnimator.mWin.mClient.dispatchGetNewSurface();
632 } catch (RemoteException e) {
633 }
634 }
635 } finally {
636 Binder.restoreCallingIdentity(callingIdentity);
637 }
638
639 return leakedSurface || killedApps;
640 }
641
642 // "Something has changed! Let's make it correct now."
643 // TODO: Super crazy long method that should be broken down...
644 void performSurfacePlacement(boolean recoveringMemory) {
645 if (DEBUG_WINDOW_TRACE) Slog.v(TAG, "performSurfacePlacementInner: entry. Called by "
646 + Debug.getCallers(3));
647
648 int i;
649 boolean updateInputWindowsNeeded = false;
650
651 if (mService.mFocusMayChange) {
652 mService.mFocusMayChange = false;
653 updateInputWindowsNeeded = mService.updateFocusedWindowLocked(
654 UPDATE_FOCUS_WILL_PLACE_SURFACES, false /*updateInputWindows*/);
655 }
656
657 // Initialize state of exiting tokens.
Wale Ogunwaleeaabfab2016-09-16 17:19:52 -0700658 final int numDisplays = mChildren.size();
Wale Ogunwalee05f5012016-09-16 16:27:29 -0700659 for (int displayNdx = 0; displayNdx < numDisplays; ++displayNdx) {
Wale Ogunwaleeaabfab2016-09-16 17:19:52 -0700660 final DisplayContent displayContent = mChildren.get(displayNdx);
Wale Ogunwalee05f5012016-09-16 16:27:29 -0700661 for (i = displayContent.mExitingTokens.size() - 1; i >= 0; i--) {
662 displayContent.mExitingTokens.get(i).hasVisible = false;
663 }
664 }
665
666 for (int stackNdx = mService.mStackIdToStack.size() - 1; stackNdx >= 0; --stackNdx) {
667 // Initialize state of exiting applications.
668 final AppTokenList exitingAppTokens =
669 mService.mStackIdToStack.valueAt(stackNdx).mExitingAppTokens;
670 for (int tokenNdx = exitingAppTokens.size() - 1; tokenNdx >= 0; --tokenNdx) {
671 exitingAppTokens.get(tokenNdx).hasVisible = false;
672 }
673 }
674
675 mHoldScreen = null;
676 mScreenBrightness = -1;
677 mButtonBrightness = -1;
678 mUserActivityTimeout = -1;
679 mObscureApplicationContentOnSecondaryDisplays = false;
680 mSustainedPerformanceModeCurrent = false;
681 mService.mTransactionSequence++;
682
683 // TODO(multi-display):
684 final DisplayContent defaultDisplay = mService.getDefaultDisplayContentLocked();
685 final DisplayInfo defaultInfo = defaultDisplay.getDisplayInfo();
686 final int defaultDw = defaultInfo.logicalWidth;
687 final int defaultDh = defaultInfo.logicalHeight;
688
689 if (SHOW_LIGHT_TRANSACTIONS) Slog.i(TAG,
690 ">>> OPEN TRANSACTION performLayoutAndPlaceSurfaces");
691 mService.openSurfaceTransaction();
692 try {
693 mService.mRoot.applySurfaceChangesTransaction(recoveringMemory, defaultDw, defaultDh);
694 } catch (RuntimeException e) {
695 Slog.wtf(TAG, "Unhandled exception in Window Manager", e);
696 } finally {
697 mService.closeSurfaceTransaction();
698 if (SHOW_LIGHT_TRANSACTIONS) Slog.i(TAG,
699 "<<< CLOSE TRANSACTION performLayoutAndPlaceSurfaces");
700 }
701
702 final WindowList defaultWindows = defaultDisplay.getWindowList();
703 final WindowSurfacePlacer surfacePlacer = mService.mWindowPlacerLocked;
704
705 // If we are ready to perform an app transition, check through all of the app tokens to be
706 // shown and see if they are ready to go.
707 if (mService.mAppTransition.isReady()) {
708 defaultDisplay.pendingLayoutChanges |=
709 surfacePlacer.handleAppTransitionReadyLocked(defaultWindows);
710 if (DEBUG_LAYOUT_REPEATS)
711 surfacePlacer.debugLayoutRepeats("after handleAppTransitionReadyLocked",
712 defaultDisplay.pendingLayoutChanges);
713 }
714
715 if (!mService.mAnimator.mAppWindowAnimating && mService.mAppTransition.isRunning()) {
716 // We have finished the animation of an app transition. To do this, we have delayed a
717 // lot of operations like showing and hiding apps, moving apps in Z-order, etc. The app
718 // token list reflects the correct Z-order, but the window list may now be out of sync
719 // with it. So here we will just rebuild the entire app window list. Fun!
720 defaultDisplay.pendingLayoutChanges |=
721 mService.handleAnimatingStoppedAndTransitionLocked();
722 if (DEBUG_LAYOUT_REPEATS)
723 surfacePlacer.debugLayoutRepeats("after handleAnimStopAndXitionLock",
724 defaultDisplay.pendingLayoutChanges);
725 }
726
727 if (mWallpaperForceHidingChanged && defaultDisplay.pendingLayoutChanges == 0
728 && !mService.mAppTransition.isReady()) {
729 // At this point, there was a window with a wallpaper that was force hiding other
730 // windows behind it, but now it is going away. This may be simple -- just animate away
731 // the wallpaper and its window -- or it may be hard -- the wallpaper now needs to be
732 // shown behind something that was hidden.
733 defaultDisplay.pendingLayoutChanges |= FINISH_LAYOUT_REDO_LAYOUT;
734 if (DEBUG_LAYOUT_REPEATS) surfacePlacer.debugLayoutRepeats(
735 "after animateAwayWallpaperLocked", defaultDisplay.pendingLayoutChanges);
736 }
737 mWallpaperForceHidingChanged = false;
738
739 if (mWallpaperMayChange) {
740 if (DEBUG_WALLPAPER_LIGHT) Slog.v(TAG, "Wallpaper may change! Adjusting");
741 defaultDisplay.pendingLayoutChanges |= FINISH_LAYOUT_REDO_WALLPAPER;
742 if (DEBUG_LAYOUT_REPEATS) surfacePlacer.debugLayoutRepeats("WallpaperMayChange",
743 defaultDisplay.pendingLayoutChanges);
744 }
745
746 if (mService.mFocusMayChange) {
747 mService.mFocusMayChange = false;
748 if (mService.updateFocusedWindowLocked(UPDATE_FOCUS_PLACING_SURFACES,
749 false /*updateInputWindows*/)) {
750 updateInputWindowsNeeded = true;
751 defaultDisplay.pendingLayoutChanges |= FINISH_LAYOUT_REDO_ANIM;
752 }
753 }
754
Wale Ogunwale2b06bfc2016-09-28 14:17:05 -0700755 if (isLayoutNeeded()) {
Wale Ogunwalee05f5012016-09-16 16:27:29 -0700756 defaultDisplay.pendingLayoutChanges |= FINISH_LAYOUT_REDO_LAYOUT;
757 if (DEBUG_LAYOUT_REPEATS) surfacePlacer.debugLayoutRepeats("mLayoutNeeded",
758 defaultDisplay.pendingLayoutChanges);
759 }
760
761 for (i = mService.mResizingWindows.size() - 1; i >= 0; i--) {
762 WindowState win = mService.mResizingWindows.get(i);
763 if (win.mAppFreezing) {
764 // Don't remove this window until rotation has completed.
765 continue;
766 }
767 // Discard the saved surface if window size is changed, it can't be reused.
768 if (win.mAppToken != null) {
769 win.mAppToken.destroySavedSurfaces();
770 }
771 win.reportResized();
772 mService.mResizingWindows.remove(i);
773 }
774
775 if (DEBUG_ORIENTATION && mService.mDisplayFrozen) Slog.v(TAG,
776 "With display frozen, orientationChangeComplete=" + mOrientationChangeComplete);
777 if (mOrientationChangeComplete) {
778 if (mService.mWindowsFreezingScreen != WINDOWS_FREEZING_SCREENS_NONE) {
779 mService.mWindowsFreezingScreen = WINDOWS_FREEZING_SCREENS_NONE;
780 mService.mLastFinishedFreezeSource = mLastWindowFreezeSource;
781 mService.mH.removeMessages(WINDOW_FREEZE_TIMEOUT);
782 }
783 mService.stopFreezingDisplayLocked();
784 }
785
786 // Destroy the surface of any windows that are no longer visible.
787 boolean wallpaperDestroyed = false;
788 i = mService.mDestroySurface.size();
789 if (i > 0) {
790 do {
791 i--;
792 WindowState win = mService.mDestroySurface.get(i);
793 win.mDestroying = false;
794 if (mService.mInputMethodWindow == win) {
795 mService.mInputMethodWindow = null;
796 }
797 if (mService.mWallpaperControllerLocked.isWallpaperTarget(win)) {
798 wallpaperDestroyed = true;
799 }
800 win.destroyOrSaveSurface();
801 } while (i > 0);
802 mService.mDestroySurface.clear();
803 }
804
805 // Time to remove any exiting tokens?
806 for (int displayNdx = 0; displayNdx < numDisplays; ++displayNdx) {
Wale Ogunwaleeaabfab2016-09-16 17:19:52 -0700807 final DisplayContent displayContent = mChildren.get(displayNdx);
Wale Ogunwalee05f5012016-09-16 16:27:29 -0700808 ArrayList<WindowToken> exitingTokens = displayContent.mExitingTokens;
809 for (i = exitingTokens.size() - 1; i >= 0; i--) {
810 WindowToken token = exitingTokens.get(i);
811 if (!token.hasVisible) {
812 exitingTokens.remove(i);
813 if (token.windowType == TYPE_WALLPAPER) {
814 mService.mWallpaperControllerLocked.removeWallpaperToken(token);
815 }
816 }
817 }
818 }
819
820 // Time to remove any exiting applications?
821 for (int stackNdx = mService.mStackIdToStack.size() - 1; stackNdx >= 0; --stackNdx) {
822 // Initialize state of exiting applications.
823 final AppTokenList exitingAppTokens =
824 mService.mStackIdToStack.valueAt(stackNdx).mExitingAppTokens;
825 for (i = exitingAppTokens.size() - 1; i >= 0; i--) {
826 final AppWindowToken token = exitingAppTokens.get(i);
827 if (!token.hasVisible && !mService.mClosingApps.contains(token) &&
828 (!token.mIsExiting || token.isEmpty())) {
829 // Make sure there is no animation running on this token, so any windows
830 // associated with it will be removed as soon as their animations are complete
831 token.mAppAnimator.clearAnimation();
832 token.mAppAnimator.animating = false;
833 if (DEBUG_ADD_REMOVE || DEBUG_TOKEN_MOVEMENT) Slog.v(TAG,
834 "performLayout: App token exiting now removed" + token);
835 token.removeIfPossible();
836 }
837 }
838 }
839
840 if (wallpaperDestroyed) {
841 defaultDisplay.pendingLayoutChanges |= FINISH_LAYOUT_REDO_WALLPAPER;
Wale Ogunwale2b06bfc2016-09-28 14:17:05 -0700842 defaultDisplay.setLayoutNeeded();
Wale Ogunwalee05f5012016-09-16 16:27:29 -0700843 }
844
845 for (int displayNdx = 0; displayNdx < numDisplays; ++displayNdx) {
Wale Ogunwaleeaabfab2016-09-16 17:19:52 -0700846 final DisplayContent displayContent = mChildren.get(displayNdx);
Wale Ogunwalee05f5012016-09-16 16:27:29 -0700847 if (displayContent.pendingLayoutChanges != 0) {
Wale Ogunwale2b06bfc2016-09-28 14:17:05 -0700848 displayContent.setLayoutNeeded();
Wale Ogunwalee05f5012016-09-16 16:27:29 -0700849 }
850 }
851
852 // Finally update all input windows now that the window changes have stabilized.
853 mService.mInputMonitor.updateInputWindowsLw(true /*force*/);
854
855 mService.setHoldScreenLocked(mHoldScreen);
856 if (!mService.mDisplayFrozen) {
857 if (mScreenBrightness < 0 || mScreenBrightness > 1.0f) {
858 mService.mPowerManagerInternal.setScreenBrightnessOverrideFromWindowManager(-1);
859 } else {
860 mService.mPowerManagerInternal.setScreenBrightnessOverrideFromWindowManager(
861 toBrightnessOverride(mScreenBrightness));
862 }
863 if (mButtonBrightness < 0 || mButtonBrightness > 1.0f) {
864 mService.mPowerManagerInternal.setButtonBrightnessOverrideFromWindowManager(-1);
865 } else {
866 mService.mPowerManagerInternal.setButtonBrightnessOverrideFromWindowManager(
867 toBrightnessOverride(mButtonBrightness));
868 }
869 mService.mPowerManagerInternal.setUserActivityTimeoutOverrideFromWindowManager(
870 mUserActivityTimeout);
871 }
872
873 if (mSustainedPerformanceModeCurrent != mSustainedPerformanceModeEnabled) {
874 mSustainedPerformanceModeEnabled = mSustainedPerformanceModeCurrent;
875 mService.mPowerManagerInternal.powerHint(
876 mService.mPowerManagerInternal.POWER_HINT_SUSTAINED_PERFORMANCE_MODE,
877 (mSustainedPerformanceModeEnabled ? 1 : 0));
878 }
879
880 if (mService.mTurnOnScreen) {
881 if (mService.mAllowTheaterModeWakeFromLayout
882 || Settings.Global.getInt(mService.mContext.getContentResolver(),
883 Settings.Global.THEATER_MODE_ON, 0) == 0) {
884 if (DEBUG_VISIBILITY || DEBUG_POWER) {
885 Slog.v(TAG, "Turning screen on after layout!");
886 }
887 mService.mPowerManager.wakeUp(SystemClock.uptimeMillis(),
888 "android.server.wm:TURN_ON");
889 }
890 mService.mTurnOnScreen = false;
891 }
892
893 if (mUpdateRotation) {
894 if (DEBUG_ORIENTATION) Slog.d(TAG, "Performing post-rotate rotation");
895 if (mService.updateRotationUncheckedLocked(false)) {
896 mService.mH.sendEmptyMessage(SEND_NEW_CONFIGURATION);
897 } else {
898 mUpdateRotation = false;
899 }
900 }
901
902 if (mService.mWaitingForDrawnCallback != null ||
Wale Ogunwale2b06bfc2016-09-28 14:17:05 -0700903 (mOrientationChangeComplete && !defaultDisplay.isLayoutNeeded()
904 && !mUpdateRotation)) {
Wale Ogunwalee05f5012016-09-16 16:27:29 -0700905 mService.checkDrawnWindowsLocked();
906 }
907
908 final int N = mService.mPendingRemove.size();
909 if (N > 0) {
910 if (mService.mPendingRemoveTmp.length < N) {
911 mService.mPendingRemoveTmp = new WindowState[N+10];
912 }
913 mService.mPendingRemove.toArray(mService.mPendingRemoveTmp);
914 mService.mPendingRemove.clear();
915 DisplayContentList displayList = new DisplayContentList();
916 for (i = 0; i < N; i++) {
917 final WindowState w = mService.mPendingRemoveTmp[i];
918 w.removeImmediately();
919 final DisplayContent displayContent = w.getDisplayContent();
920 if (displayContent != null && !displayList.contains(displayContent)) {
921 displayList.add(displayContent);
922 }
923 }
924
925 for (DisplayContent displayContent : displayList) {
926 mService.mLayersController.assignLayersLocked(displayContent.getWindowList());
Wale Ogunwale2b06bfc2016-09-28 14:17:05 -0700927 displayContent.setLayoutNeeded();
Wale Ogunwalee05f5012016-09-16 16:27:29 -0700928 }
929 }
930
931 // Remove all deferred displays stacks, tasks, and activities.
Wale Ogunwaleeaabfab2016-09-16 17:19:52 -0700932 for (int displayNdx = mChildren.size() - 1; displayNdx >= 0; --displayNdx) {
933 mChildren.get(displayNdx).checkCompleteDeferredRemoval();
Wale Ogunwalee05f5012016-09-16 16:27:29 -0700934 }
935
936 if (updateInputWindowsNeeded) {
937 mService.mInputMonitor.updateInputWindowsLw(false /*force*/);
938 }
939 mService.setFocusTaskRegionLocked();
940
941 // Check to see if we are now in a state where the screen should
942 // be enabled, because the window obscured flags have changed.
943 mService.enableScreenIfNeededLocked();
944
945 mService.scheduleAnimationLocked();
946 mService.mWindowPlacerLocked.destroyPendingSurfaces();
947
948 if (DEBUG_WINDOW_TRACE) Slog.e(TAG,
949 "performSurfacePlacementInner exit: animating=" + mService.mAnimator.isAnimating());
950 }
951
952 // TODO: Super crazy long method that should be broken down...
Wale Ogunwale2b06bfc2016-09-28 14:17:05 -0700953 private void applySurfaceChangesTransaction(boolean recoveringMemory, int defaultDw, int defaultDh) {
Wale Ogunwalee05f5012016-09-16 16:27:29 -0700954 mHoldScreenWindow = null;
955 mObsuringWindow = null;
956
957 if (mService.mWatermark != null) {
958 mService.mWatermark.positionSurface(defaultDw, defaultDh);
959 }
960 if (mService.mStrictModeFlash != null) {
961 mService.mStrictModeFlash.positionSurface(defaultDw, defaultDh);
962 }
963 if (mService.mCircularDisplayMask != null) {
964 mService.mCircularDisplayMask.positionSurface(defaultDw, defaultDh, mService.mRotation);
965 }
966 if (mService.mEmulatorDisplayOverlay != null) {
967 mService.mEmulatorDisplayOverlay.positionSurface(defaultDw, defaultDh,
968 mService.mRotation);
969 }
970
971 boolean focusDisplayed = false;
972
Wale Ogunwaleeaabfab2016-09-16 17:19:52 -0700973 final int count = mChildren.size();
Wale Ogunwalee05f5012016-09-16 16:27:29 -0700974 for (int j = 0; j < count; ++j) {
Wale Ogunwaleeaabfab2016-09-16 17:19:52 -0700975 final DisplayContent dc = mChildren.get(j);
Wale Ogunwalee05f5012016-09-16 16:27:29 -0700976 boolean updateAllDrawn = false;
977 WindowList windows = dc.getWindowList();
978 DisplayInfo displayInfo = dc.getDisplayInfo();
979 final int displayId = dc.getDisplayId();
980 final int dw = displayInfo.logicalWidth;
981 final int dh = displayInfo.logicalHeight;
982 final boolean isDefaultDisplay = (displayId == Display.DEFAULT_DISPLAY);
983 final WindowSurfacePlacer surfacePlacer = mService.mWindowPlacerLocked;
984
985 // Reset for each display.
986 mDisplayHasContent = false;
987 mPreferredRefreshRate = 0;
988 mPreferredModeId = 0;
989
990 int repeats = 0;
991 do {
992 repeats++;
993 if (repeats > 6) {
994 Slog.w(TAG, "Animation repeat aborted after too many iterations");
Wale Ogunwale2b06bfc2016-09-28 14:17:05 -0700995 dc.clearLayoutNeeded();
Wale Ogunwalee05f5012016-09-16 16:27:29 -0700996 break;
997 }
998
999 if (DEBUG_LAYOUT_REPEATS) surfacePlacer.debugLayoutRepeats(
1000 "On entry to LockedInner", dc.pendingLayoutChanges);
1001
1002 if ((dc.pendingLayoutChanges & FINISH_LAYOUT_REDO_WALLPAPER) != 0
1003 && mService.mWallpaperControllerLocked.adjustWallpaperWindows()) {
1004 mService.mLayersController.assignLayersLocked(windows);
Wale Ogunwale2b06bfc2016-09-28 14:17:05 -07001005 dc.setLayoutNeeded();
Wale Ogunwalee05f5012016-09-16 16:27:29 -07001006 }
1007
1008 if (isDefaultDisplay
1009 && (dc.pendingLayoutChanges & FINISH_LAYOUT_REDO_CONFIG) != 0) {
1010 if (DEBUG_LAYOUT) Slog.v(TAG, "Computing new config from layout");
1011 if (mService.updateOrientationFromAppTokensLocked(true)) {
Wale Ogunwale2b06bfc2016-09-28 14:17:05 -07001012 dc.setLayoutNeeded();
Wale Ogunwalee05f5012016-09-16 16:27:29 -07001013 mService.mH.sendEmptyMessage(SEND_NEW_CONFIGURATION);
1014 }
1015 }
1016
1017 if ((dc.pendingLayoutChanges & FINISH_LAYOUT_REDO_LAYOUT) != 0) {
Wale Ogunwale2b06bfc2016-09-28 14:17:05 -07001018 dc.setLayoutNeeded();
Wale Ogunwalee05f5012016-09-16 16:27:29 -07001019 }
1020
1021 // FIRST LOOP: Perform a layout, if needed.
1022 if (repeats < LAYOUT_REPEAT_THRESHOLD) {
1023 surfacePlacer.performLayoutLockedInner(dc, repeats == 1,
1024 false /* updateInputWindows */);
1025 } else {
1026 Slog.w(TAG, "Layout repeat skipped after too many iterations");
1027 }
1028
1029 // FIRST AND ONE HALF LOOP: Make WindowManagerPolicy think
1030 // it is animating.
1031 dc.pendingLayoutChanges = 0;
1032
1033 if (isDefaultDisplay) {
1034 mService.mPolicy.beginPostLayoutPolicyLw(dw, dh);
1035 for (int i = windows.size() - 1; i >= 0; i--) {
1036 WindowState w = windows.get(i);
1037 if (w.mHasSurface) {
1038 mService.mPolicy.applyPostLayoutPolicyLw(
1039 w, w.mAttrs, w.getParentWindow());
1040 }
1041 }
1042 dc.pendingLayoutChanges |=
1043 mService.mPolicy.finishPostLayoutPolicyLw();
1044 if (DEBUG_LAYOUT_REPEATS) surfacePlacer.debugLayoutRepeats(
1045 "after finishPostLayoutPolicyLw", dc.pendingLayoutChanges);
1046 }
1047 } while (dc.pendingLayoutChanges != 0);
1048
1049 mObscured = false;
1050 mSyswin = false;
1051 dc.resetDimming();
1052
1053 // Only used if default window
1054 final boolean someoneLosingFocus = !mService.mLosingFocus.isEmpty();
1055
1056 for (int i = windows.size() - 1; i >= 0; i--) {
1057 WindowState w = windows.get(i);
1058 final Task task = w.getTask();
1059 final boolean obscuredChanged = w.mObscured != mObscured;
1060
1061 // Update effect.
1062 w.mObscured = mObscured;
1063 if (!mObscured) {
1064 handleNotObscuredLocked(w, displayInfo);
1065 }
1066
1067 w.applyDimLayerIfNeeded();
1068
1069 if (isDefaultDisplay && obscuredChanged && w.isVisibleLw()
1070 && mService.mWallpaperControllerLocked.isWallpaperTarget(w)) {
1071 // This is the wallpaper target and its obscured state changed... make sure the
1072 // current wallaper's visibility has been updated accordingly.
1073 mService.mWallpaperControllerLocked.updateWallpaperVisibility();
1074 }
1075
1076 final WindowStateAnimator winAnimator = w.mWinAnimator;
1077
1078 // If the window has moved due to its containing content frame changing, then
1079 // notify the listeners and optionally animate it. Simply checking a change of
1080 // position is not enough, because being move due to dock divider is not a trigger
1081 // for animation.
1082 if (w.hasMoved()) {
1083 // Frame has moved, containing content frame has also moved, and we're not
1084 // currently animating... let's do something.
1085 final int left = w.mFrame.left;
1086 final int top = w.mFrame.top;
1087 final boolean adjustedForMinimizedDockOrIme = task != null
1088 && (task.mStack.isAdjustedForMinimizedDockedStack()
1089 || task.mStack.isAdjustedForIme());
Robert Carr67e7b402016-09-23 16:40:02 -07001090 if (mService.okToDisplay()
1091 && (w.mAttrs.privateFlags & PRIVATE_FLAG_NO_MOVE_ANIMATION) == 0
Wale Ogunwalee05f5012016-09-16 16:27:29 -07001092 && !w.isDragResizing() && !adjustedForMinimizedDockOrIme
1093 && (task == null || w.getTask().mStack.hasMovementAnimations())
1094 && !w.mWinAnimator.mLastHidden) {
1095 winAnimator.setMoveAnimation(left, top);
1096 }
1097
1098 //TODO (multidisplay): Accessibility supported only for the default display.
1099 if (mService.mAccessibilityController != null
1100 && displayId == Display.DEFAULT_DISPLAY) {
1101 mService.mAccessibilityController.onSomeWindowResizedOrMovedLocked();
1102 }
1103
1104 try {
1105 w.mClient.moved(left, top);
1106 } catch (RemoteException e) {
1107 }
1108 w.mMovedByResize = false;
1109 }
1110
1111 //Slog.i(TAG, "Window " + this + " clearing mContentChanged - done placing");
1112 w.mContentChanged = false;
1113
1114 // Moved from updateWindowsAndWallpaperLocked().
1115 if (w.mHasSurface) {
1116 // Take care of the window being ready to display.
1117 final boolean committed = winAnimator.commitFinishDrawingLocked();
1118 if (isDefaultDisplay && committed) {
1119 if (w.mAttrs.type == TYPE_DREAM) {
1120 // HACK: When a dream is shown, it may at that point hide the lock
1121 // screen. So we need to redo the layout to let the phone window manager
1122 // make this happen.
1123 dc.pendingLayoutChanges |= FINISH_LAYOUT_REDO_LAYOUT;
1124 if (DEBUG_LAYOUT_REPEATS) {
1125 surfacePlacer.debugLayoutRepeats(
1126 "dream and commitFinishDrawingLocked true",
1127 dc.pendingLayoutChanges);
1128 }
1129 }
1130 if ((w.mAttrs.flags & FLAG_SHOW_WALLPAPER) != 0) {
1131 if (DEBUG_WALLPAPER_LIGHT)
1132 Slog.v(TAG, "First draw done in potential wallpaper target " + w);
1133 mWallpaperMayChange = true;
1134 dc.pendingLayoutChanges |= FINISH_LAYOUT_REDO_WALLPAPER;
1135 if (DEBUG_LAYOUT_REPEATS) {
1136 surfacePlacer.debugLayoutRepeats(
1137 "wallpaper and commitFinishDrawingLocked true",
1138 dc.pendingLayoutChanges);
1139 }
1140 }
1141 }
1142 if (!winAnimator.isAnimationStarting() && !winAnimator.isWaitingForOpening()) {
1143 // Updates the shown frame before we set up the surface. This is needed
1144 // because the resizing could change the top-left position (in addition to
1145 // size) of the window. setSurfaceBoundariesLocked uses mShownPosition to
1146 // position the surface.
1147 //
1148 // If an animation is being started, we can't call this method because the
1149 // animation hasn't processed its initial transformation yet, but in general
1150 // we do want to update the position if the window is animating.
1151 winAnimator.computeShownFrameLocked();
1152 }
1153 winAnimator.setSurfaceBoundariesLocked(recoveringMemory);
1154 }
1155
1156 final AppWindowToken atoken = w.mAppToken;
1157 if (DEBUG_STARTING_WINDOW && atoken != null && w == atoken.startingWindow) {
1158 Slog.d(TAG, "updateWindows: starting " + w
1159 + " isOnScreen=" + w.isOnScreen() + " allDrawn=" + atoken.allDrawn
1160 + " freezingScreen=" + atoken.mAppAnimator.freezingScreen);
1161 }
1162 if (atoken != null && (!atoken.allDrawn || !atoken.allDrawnExcludingSaved
1163 || atoken.mAppAnimator.freezingScreen)) {
1164 if (atoken.lastTransactionSequence != mService.mTransactionSequence) {
1165 atoken.lastTransactionSequence = mService.mTransactionSequence;
1166 atoken.numInterestingWindows = atoken.numDrawnWindows = 0;
1167 atoken.numInterestingWindowsExcludingSaved = 0;
1168 atoken.numDrawnWindowsExcludingSaved = 0;
1169 atoken.startingDisplayed = false;
1170 }
1171 if (!atoken.allDrawn && w.mightAffectAllDrawn(false /* visibleOnly */)) {
1172 if (DEBUG_VISIBILITY || DEBUG_ORIENTATION) {
1173 Slog.v(TAG, "Eval win " + w + ": isDrawn="
1174 + w.isDrawnLw()
1175 + ", isAnimationSet=" + winAnimator.isAnimationSet());
1176 if (!w.isDrawnLw()) {
1177 Slog.v(TAG, "Not displayed: s="
1178 + winAnimator.mSurfaceController
1179 + " pv=" + w.mPolicyVisibility
1180 + " mDrawState=" + winAnimator.drawStateToString()
1181 + " ph=" + w.isParentWindowHidden()
1182 + " th=" + atoken.hiddenRequested
1183 + " a=" + winAnimator.mAnimating);
1184 }
1185 }
1186 if (w != atoken.startingWindow) {
1187 if (w.isInteresting()) {
1188 atoken.numInterestingWindows++;
1189 if (w.isDrawnLw()) {
1190 atoken.numDrawnWindows++;
1191 if (DEBUG_VISIBILITY || DEBUG_ORIENTATION)
1192 Slog.v(TAG, "tokenMayBeDrawn: " + atoken
1193 + " w=" + w + " numInteresting="
1194 + atoken.numInterestingWindows
1195 + " freezingScreen="
1196 + atoken.mAppAnimator.freezingScreen
1197 + " mAppFreezing=" + w.mAppFreezing);
1198 updateAllDrawn = true;
1199 }
1200 }
1201 } else if (w.isDrawnLw()) {
1202 mService.mH.sendEmptyMessage(NOTIFY_STARTING_WINDOW_DRAWN);
1203 atoken.startingDisplayed = true;
1204 }
1205 }
1206 if (!atoken.allDrawnExcludingSaved
1207 && w.mightAffectAllDrawn(true /* visibleOnly */)) {
1208 if (w != atoken.startingWindow && w.isInteresting()) {
1209 atoken.numInterestingWindowsExcludingSaved++;
1210 if (w.isDrawnLw() && !w.isAnimatingWithSavedSurface()) {
1211 atoken.numDrawnWindowsExcludingSaved++;
1212 if (DEBUG_VISIBILITY || DEBUG_ORIENTATION)
1213 Slog.v(TAG, "tokenMayBeDrawnExcludingSaved: " + atoken
1214 + " w=" + w + " numInteresting="
1215 + atoken.numInterestingWindowsExcludingSaved
1216 + " freezingScreen="
1217 + atoken.mAppAnimator.freezingScreen
1218 + " mAppFreezing=" + w.mAppFreezing);
1219 updateAllDrawn = true;
1220 }
1221 }
1222 }
1223 }
1224
1225 if (isDefaultDisplay && someoneLosingFocus && w == mService.mCurrentFocus
1226 && w.isDisplayedLw()) {
1227 focusDisplayed = true;
1228 }
1229
1230 mService.updateResizingWindows(w);
1231 }
1232
1233 mService.mDisplayManagerInternal.setDisplayProperties(displayId,
1234 mDisplayHasContent,
1235 mPreferredRefreshRate,
1236 mPreferredModeId,
1237 true /* inTraversal, must call performTraversalInTrans... below */);
1238
1239 dc.stopDimmingIfNeeded();
1240
1241 if (updateAllDrawn) {
1242 // See if any windows have been drawn, so they (and others associated with them)
1243 // can now be shown.
1244 dc.updateAllDrawn();
1245 }
1246 }
1247
1248 if (focusDisplayed) {
1249 mService.mH.sendEmptyMessage(REPORT_LOSING_FOCUS);
1250 }
1251
1252 // Give the display manager a chance to adjust properties
1253 // like display rotation if it needs to.
1254 mService.mDisplayManagerInternal.performTraversalInTransactionFromWindowManager();
1255 }
1256
1257 /**
1258 * @param w WindowState this method is applied to.
1259 * @param dispInfo info of the display that the window's obscuring state is checked against.
1260 */
1261 private void handleNotObscuredLocked(final WindowState w, final DisplayInfo dispInfo) {
1262 final WindowManager.LayoutParams attrs = w.mAttrs;
1263 final int attrFlags = attrs.flags;
1264 final boolean canBeSeen = w.isDisplayedLw();
1265 final int privateflags = attrs.privateFlags;
1266
1267 if (canBeSeen && w.isObscuringFullscreen(dispInfo)) {
1268 // This window completely covers everything behind it,
1269 // so we want to leave all of them as undimmed (for
1270 // performance reasons).
1271 if (!mObscured) {
1272 mObsuringWindow = w;
1273 }
1274
1275 mObscured = true;
1276 }
1277
1278 if (w.mHasSurface && canBeSeen) {
1279 if ((attrFlags & FLAG_KEEP_SCREEN_ON) != 0) {
1280 mHoldScreen = w.mSession;
1281 mHoldScreenWindow = w;
1282 } else if (DEBUG_KEEP_SCREEN_ON && w == mService.mLastWakeLockHoldingWindow) {
1283 Slog.d(TAG_KEEP_SCREEN_ON, "handleNotObscuredLocked: " + w + " was holding "
1284 + "screen wakelock but no longer has FLAG_KEEP_SCREEN_ON!!! called by"
1285 + Debug.getCallers(10));
1286 }
1287 if (!mSyswin && w.mAttrs.screenBrightness >= 0 && mScreenBrightness < 0) {
1288 mScreenBrightness = w.mAttrs.screenBrightness;
1289 }
1290 if (!mSyswin && w.mAttrs.buttonBrightness >= 0 && mButtonBrightness < 0) {
1291 mButtonBrightness = w.mAttrs.buttonBrightness;
1292 }
1293 if (!mSyswin && w.mAttrs.userActivityTimeout >= 0 && mUserActivityTimeout < 0) {
1294 mUserActivityTimeout = w.mAttrs.userActivityTimeout;
1295 }
1296
1297 final int type = attrs.type;
1298 if (type == TYPE_SYSTEM_DIALOG || type == TYPE_SYSTEM_ERROR
1299 || (attrs.privateFlags & PRIVATE_FLAG_KEYGUARD) != 0) {
1300 mSyswin = true;
1301 }
1302
1303 // This function assumes that the contents of the default display are processed first
1304 // before secondary displays.
1305 final DisplayContent displayContent = w.getDisplayContent();
1306 if (displayContent != null && displayContent.isDefaultDisplay) {
1307 // While a dream or keyguard is showing, obscure ordinary application content on
1308 // secondary displays (by forcibly enabling mirroring unless there is other content
1309 // we want to show) but still allow opaque keyguard dialogs to be shown.
1310 if (type == TYPE_DREAM || (attrs.privateFlags & PRIVATE_FLAG_KEYGUARD) != 0) {
1311 mObscureApplicationContentOnSecondaryDisplays = true;
1312 }
1313 mDisplayHasContent = true;
1314 } else if (displayContent != null &&
1315 (!mObscureApplicationContentOnSecondaryDisplays
1316 || (mObscured && type == TYPE_KEYGUARD_DIALOG))) {
1317 // Allow full screen keyguard presentation dialogs to be seen.
1318 mDisplayHasContent = true;
1319 }
1320 if (mPreferredRefreshRate == 0 && w.mAttrs.preferredRefreshRate != 0) {
1321 mPreferredRefreshRate = w.mAttrs.preferredRefreshRate;
1322 }
1323 if (mPreferredModeId == 0 && w.mAttrs.preferredDisplayModeId != 0) {
1324 mPreferredModeId = w.mAttrs.preferredDisplayModeId;
1325 }
1326 if ((privateflags & PRIVATE_FLAG_SUSTAINED_PERFORMANCE_MODE) != 0) {
1327 mSustainedPerformanceModeCurrent = true;
1328 }
1329 }
1330 }
1331
1332 boolean copyAnimToLayoutParams() {
1333 boolean doRequest = false;
1334
1335 final int bulkUpdateParams = mService.mAnimator.mBulkUpdateParams;
1336 if ((bulkUpdateParams & SET_UPDATE_ROTATION) != 0) {
1337 mUpdateRotation = true;
1338 doRequest = true;
1339 }
1340 if ((bulkUpdateParams & SET_WALLPAPER_MAY_CHANGE) != 0) {
1341 mWallpaperMayChange = true;
1342 doRequest = true;
1343 }
1344 if ((bulkUpdateParams & SET_FORCE_HIDING_CHANGED) != 0) {
1345 mWallpaperForceHidingChanged = true;
1346 doRequest = true;
1347 }
1348 if ((bulkUpdateParams & SET_ORIENTATION_CHANGE_COMPLETE) == 0) {
1349 mOrientationChangeComplete = false;
1350 } else {
1351 mOrientationChangeComplete = true;
1352 mLastWindowFreezeSource = mService.mAnimator.mLastWindowFreezeSource;
1353 if (mService.mWindowsFreezingScreen != WINDOWS_FREEZING_SCREENS_NONE) {
1354 doRequest = true;
1355 }
1356 }
1357 if ((bulkUpdateParams & SET_TURN_ON_SCREEN) != 0) {
1358 mService.mTurnOnScreen = true;
1359 }
1360 if ((bulkUpdateParams & SET_WALLPAPER_ACTION_PENDING) != 0) {
1361 mWallpaperActionPending = true;
1362 }
1363
1364 return doRequest;
1365 }
1366
1367 private static int toBrightnessOverride(float value) {
1368 return (int)(value * PowerManager.BRIGHTNESS_ON);
1369 }
1370
1371 void enableSurfaceTrace(ParcelFileDescriptor pfd) {
1372 final FileDescriptor fd = pfd.getFileDescriptor();
1373 if (mSurfaceTraceEnabled) {
1374 disableSurfaceTrace();
1375 }
1376 mSurfaceTraceEnabled = true;
1377 mRemoteEventTrace = new RemoteEventTrace(mService, fd);
1378 mSurfaceTraceFd = pfd;
Wale Ogunwaleeaabfab2016-09-16 17:19:52 -07001379 for (int displayNdx = mChildren.size() - 1; displayNdx >= 0; --displayNdx) {
1380 final DisplayContent dc = mChildren.get(displayNdx);
Wale Ogunwalee05f5012016-09-16 16:27:29 -07001381 dc.enableSurfaceTrace(fd);
1382 }
1383 }
1384
1385 void disableSurfaceTrace() {
1386 mSurfaceTraceEnabled = false;
1387 mRemoteEventTrace = null;
1388 mSurfaceTraceFd = null;
Wale Ogunwaleeaabfab2016-09-16 17:19:52 -07001389 for (int displayNdx = mChildren.size() - 1; displayNdx >= 0; --displayNdx) {
1390 final DisplayContent dc = mChildren.get(displayNdx);
Wale Ogunwalee05f5012016-09-16 16:27:29 -07001391 dc.disableSurfaceTrace();
1392 }
1393 }
1394
1395 void dumpDisplayContents(PrintWriter pw) {
1396 pw.println("WINDOW MANAGER DISPLAY CONTENTS (dumpsys window displays)");
1397 if (mService.mDisplayReady) {
Wale Ogunwaleeaabfab2016-09-16 17:19:52 -07001398 final int count = mChildren.size();
Wale Ogunwalee05f5012016-09-16 16:27:29 -07001399 for (int i = 0; i < count; ++i) {
Wale Ogunwaleeaabfab2016-09-16 17:19:52 -07001400 final DisplayContent displayContent = mChildren.get(i);
Wale Ogunwalee05f5012016-09-16 16:27:29 -07001401 displayContent.dump(" ", pw);
1402 }
1403 } else {
1404 pw.println(" NO DISPLAY");
1405 }
1406 }
1407
1408 void dumpLayoutNeededDisplayIds(PrintWriter pw) {
Wale Ogunwale2b06bfc2016-09-28 14:17:05 -07001409 if (!isLayoutNeeded()) {
Wale Ogunwalee05f5012016-09-16 16:27:29 -07001410 return;
1411 }
Wale Ogunwale2b06bfc2016-09-28 14:17:05 -07001412 pw.print(" mLayoutNeeded on displays=");
Wale Ogunwaleeaabfab2016-09-16 17:19:52 -07001413 final int count = mChildren.size();
Wale Ogunwalee05f5012016-09-16 16:27:29 -07001414 for (int displayNdx = 0; displayNdx < count; ++displayNdx) {
Wale Ogunwaleeaabfab2016-09-16 17:19:52 -07001415 final DisplayContent displayContent = mChildren.get(displayNdx);
Wale Ogunwale2b06bfc2016-09-28 14:17:05 -07001416 if (displayContent.isLayoutNeeded()) {
Wale Ogunwalee05f5012016-09-16 16:27:29 -07001417 pw.print(displayContent.getDisplayId());
1418 }
1419 }
1420 pw.println();
1421 }
1422
1423 void dumpWindowsNoHeader(PrintWriter pw, boolean dumpAll, ArrayList<WindowState> windows) {
Wale Ogunwaleeaabfab2016-09-16 17:19:52 -07001424 final int numDisplays = mChildren.size();
Wale Ogunwalee05f5012016-09-16 16:27:29 -07001425 for (int displayNdx = 0; displayNdx < numDisplays; ++displayNdx) {
Wale Ogunwaleeaabfab2016-09-16 17:19:52 -07001426 final WindowList windowList = mChildren.get(displayNdx).getWindowList();
Wale Ogunwalee05f5012016-09-16 16:27:29 -07001427 for (int winNdx = windowList.size() - 1; winNdx >= 0; --winNdx) {
1428 final WindowState w = windowList.get(winNdx);
1429 if (windows == null || windows.contains(w)) {
1430 pw.println(" Window #" + winNdx + " " + w + ":");
1431 w.dump(pw, " ", dumpAll || windows != null);
1432 }
1433 }
1434 }
1435 }
Wale Ogunwaleba51ca22016-09-23 06:06:54 -07001436
1437 @Override
1438 String getName() {
1439 return "ROOT";
1440 }
Wale Ogunwalee05f5012016-09-16 16:27:29 -07001441}