Fix transferring of starting windows
Since we may transfer starting data we can not store AppWindowToken in that class. Additionally, remove starting window directly if it was transferred. The normal removing path doesn't really work as the fields aren't set. Also fixes a monkey crash in the same code region. Test: Open a notification that creates multiple activities with using TaskStackBuilder, verify no windows leaking. Test: (For monkey crash) Boot device, pray to the monkey god Change-Id: I64fb176b579535adea1916d1623ad03ab06ca67e Fixes: 34364463 Fixes: 34361417 Fixes: 34349533
This commit is contained in:
@@ -87,7 +87,6 @@ public class AppWindowContainerController
|
||||
|
||||
private final Runnable mRemoveStartingWindow = () -> {
|
||||
StartingSurface surface = null;
|
||||
StartingData data = null;
|
||||
synchronized (mWindowMap) {
|
||||
if (DEBUG_STARTING_WINDOW) Slog.v(TAG_WM, "Remove starting " + mContainer
|
||||
+ ": startingWindow=" + mContainer.startingWindow
|
||||
@@ -97,14 +96,13 @@ public class AppWindowContainerController
|
||||
}
|
||||
if (mContainer.startingWindow != null) {
|
||||
surface = mContainer.startingSurface;
|
||||
data = mContainer.startingData;
|
||||
mContainer.startingData = null;
|
||||
mContainer.startingSurface = null;
|
||||
mContainer.startingWindow = null;
|
||||
mContainer.startingDisplayed = false;
|
||||
}
|
||||
}
|
||||
if (data != null && surface != null) {
|
||||
if (surface != null) {
|
||||
try {
|
||||
surface.remove();
|
||||
} catch (Exception e) {
|
||||
@@ -115,12 +113,14 @@ public class AppWindowContainerController
|
||||
|
||||
private final Runnable mAddStartingWindow = () -> {
|
||||
final StartingData startingData;
|
||||
final AppWindowToken container;
|
||||
|
||||
synchronized (mWindowMap) {
|
||||
if (mContainer == null) {
|
||||
return;
|
||||
}
|
||||
startingData = mContainer.startingData;
|
||||
container = mContainer;
|
||||
}
|
||||
|
||||
if (startingData == null) {
|
||||
@@ -129,41 +129,40 @@ public class AppWindowContainerController
|
||||
}
|
||||
|
||||
if (DEBUG_STARTING_WINDOW) Slog.v(TAG_WM, "Add starting "
|
||||
+ this + ": startingData=" + mContainer.startingData);
|
||||
+ this + ": startingData=" + container.startingData);
|
||||
|
||||
StartingSurface surface = null;
|
||||
try {
|
||||
surface = startingData.createStartingSurface();
|
||||
surface = startingData.createStartingSurface(container);
|
||||
} catch (Exception e) {
|
||||
Slog.w(TAG_WM, "Exception when adding starting window", e);
|
||||
}
|
||||
if (surface != null) {
|
||||
boolean abort = false;
|
||||
synchronized(mWindowMap) {
|
||||
if (mContainer.removed || mContainer.startingData == null) {
|
||||
if (container.removed || container.startingData == null) {
|
||||
// If the window was successfully added, then
|
||||
// we need to remove it.
|
||||
if (mContainer.startingWindow != null) {
|
||||
if (container.startingWindow != null) {
|
||||
if (DEBUG_STARTING_WINDOW) Slog.v(TAG_WM,
|
||||
"Aborted starting " + mContainer
|
||||
+ ": removed=" + mContainer.removed
|
||||
+ " startingData=" + mContainer.startingData);
|
||||
"Aborted starting " + container
|
||||
+ ": removed=" + container.removed
|
||||
+ " startingData=" + container.startingData);
|
||||
container.startingWindow = null;
|
||||
container.startingData = null;
|
||||
abort = true;
|
||||
}
|
||||
} else {
|
||||
mContainer.startingSurface = surface;
|
||||
container.startingSurface = surface;
|
||||
}
|
||||
if (DEBUG_STARTING_WINDOW && !abort) Slog.v(TAG_WM,
|
||||
"Added starting " + mContainer
|
||||
+ ": startingWindow="
|
||||
+ mContainer.startingWindow + " startingView="
|
||||
+ mContainer.startingSurface);
|
||||
+ container.startingWindow + " startingView="
|
||||
+ container.startingSurface);
|
||||
}
|
||||
if (abort) {
|
||||
mRemoveStartingWindow.run();
|
||||
if (mContainer == null) {
|
||||
return;
|
||||
}
|
||||
surface.remove();
|
||||
}
|
||||
}
|
||||
};
|
||||
@@ -465,7 +464,7 @@ public class AppWindowContainerController
|
||||
}
|
||||
|
||||
if (DEBUG_STARTING_WINDOW) Slog.v(TAG_WM, "Creating StartingData");
|
||||
mContainer.startingData = new SplashScreenStartingData(mService, mContainer, pkg, theme,
|
||||
mContainer.startingData = new SplashScreenStartingData(mService, pkg, theme,
|
||||
compatInfo, nonLocalizedLabel, labelRes, icon, logo, windowFlags,
|
||||
mContainer.getMergedOverrideConfiguration());
|
||||
scheduleAddStartingWindow();
|
||||
@@ -499,8 +498,7 @@ public class AppWindowContainerController
|
||||
return false;
|
||||
}
|
||||
|
||||
mContainer.startingData = new SnapshotStartingData(mService, mContainer,
|
||||
snapshot.getSnapshot());
|
||||
mContainer.startingData = new SnapshotStartingData(mService, snapshot.getSnapshot());
|
||||
scheduleAddStartingWindow();
|
||||
return true;
|
||||
}
|
||||
|
||||
@@ -27,16 +27,14 @@ class SnapshotStartingData extends StartingData {
|
||||
private final WindowManagerService mService;
|
||||
private final GraphicBuffer mSnapshot;
|
||||
|
||||
SnapshotStartingData(WindowManagerService service, AppWindowToken appWindowToken,
|
||||
GraphicBuffer snapshot) {
|
||||
super(service, appWindowToken);
|
||||
SnapshotStartingData(WindowManagerService service, GraphicBuffer snapshot) {
|
||||
super(service);
|
||||
mService = service;
|
||||
mSnapshot = snapshot;
|
||||
}
|
||||
|
||||
@Override
|
||||
StartingSurface createStartingSurface() {
|
||||
return mService.mTaskSnapshotController.createStartingSurface(
|
||||
mAppWindowToken, mSnapshot);
|
||||
StartingSurface createStartingSurface(AppWindowToken atoken) {
|
||||
return mService.mTaskSnapshotController.createStartingSurface(atoken, mSnapshot);
|
||||
}
|
||||
}
|
||||
|
||||
@@ -35,11 +35,10 @@ class SplashScreenStartingData extends StartingData {
|
||||
private final int mWindowFlags;
|
||||
private final Configuration mMergedOverrideConfiguration;
|
||||
|
||||
SplashScreenStartingData(WindowManagerService service, AppWindowToken appWindowToken,
|
||||
String pkg, int theme, CompatibilityInfo compatInfo, CharSequence nonLocalizedLabel,
|
||||
int labelRes, int icon, int logo, int windowFlags,
|
||||
Configuration mergedOverrideConfiguration) {
|
||||
super(service, appWindowToken);
|
||||
SplashScreenStartingData(WindowManagerService service, String pkg, int theme,
|
||||
CompatibilityInfo compatInfo, CharSequence nonLocalizedLabel, int labelRes, int icon,
|
||||
int logo, int windowFlags, Configuration mergedOverrideConfiguration) {
|
||||
super(service);
|
||||
mPkg = pkg;
|
||||
mTheme = theme;
|
||||
mCompatInfo = compatInfo;
|
||||
@@ -52,8 +51,8 @@ class SplashScreenStartingData extends StartingData {
|
||||
}
|
||||
|
||||
@Override
|
||||
StartingSurface createStartingSurface() {
|
||||
return mService.mPolicy.addSplashScreen(mAppWindowToken.token, mPkg, mTheme, mCompatInfo,
|
||||
StartingSurface createStartingSurface(AppWindowToken atoken) {
|
||||
return mService.mPolicy.addSplashScreen(atoken.token, mPkg, mTheme, mCompatInfo,
|
||||
mNonLocalizedLabel, mLabelRes, mIcon, mLogo, mWindowFlags,
|
||||
mMergedOverrideConfiguration);
|
||||
}
|
||||
|
||||
@@ -24,19 +24,18 @@ import android.view.WindowManagerPolicy.StartingSurface;
|
||||
public abstract class StartingData {
|
||||
|
||||
protected final WindowManagerService mService;
|
||||
protected final AppWindowToken mAppWindowToken;
|
||||
|
||||
protected StartingData(WindowManagerService service, AppWindowToken appWindowToken) {
|
||||
protected StartingData(WindowManagerService service) {
|
||||
mService = service;
|
||||
mAppWindowToken = appWindowToken;
|
||||
}
|
||||
|
||||
/**
|
||||
* Creates the actual starting window surface. DO NOT HOLD THE WINDOW MANAGER LOCK WHEN CALLING
|
||||
* THIS METHOD.
|
||||
*
|
||||
* @param atoken the app to add the starting window to
|
||||
* @return a class implementing {@link StartingSurface} for easy removal with
|
||||
* {@link StartingSurface#remove}
|
||||
*/
|
||||
abstract StartingSurface createStartingSurface();
|
||||
abstract StartingSurface createStartingSurface(AppWindowToken atoken);
|
||||
}
|
||||
Reference in New Issue
Block a user