diff options
| author | 2024-05-16 07:59:08 +0000 | |
|---|---|---|
| committer | 2024-05-16 07:59:08 +0000 | |
| commit | 0856c9f791e86fce7a7984e75c4e3b9794bd7f81 (patch) | |
| tree | ecf053124dbf3d2c02779edc854ce0fec3d94cfd | |
| parent | cb37b042094b1d80d1b86f53cbd0a188ec7a8d55 (diff) | |
| parent | 0a5aed0ca86f70370450c191068a248cb8149e9d (diff) | |
Merge "Close TaskSnapshot's hardware buffer once no more strong reference to it." into main
6 files changed, 50 insertions, 1 deletions
diff --git a/core/java/android/window/TaskSnapshot.java b/core/java/android/window/TaskSnapshot.java index 41b6d31661ce..a2e3d40e5c6b 100644 --- a/core/java/android/window/TaskSnapshot.java +++ b/core/java/android/window/TaskSnapshot.java @@ -16,6 +16,7 @@ package android.window; +import android.annotation.IntDef; import android.annotation.NonNull; import android.compat.annotation.UnsupportedAppUsage; import android.content.ComponentName; @@ -32,6 +33,9 @@ import android.os.SystemClock; import android.view.Surface; import android.view.WindowInsetsController; +import java.lang.annotation.Retention; +import java.lang.annotation.RetentionPolicy; + /** * Represents a task snapshot. * @hide @@ -68,6 +72,21 @@ public class TaskSnapshot implements Parcelable { private final boolean mHasImeSurface; // Must be one of the named color spaces, otherwise, always use SRGB color space. private final ColorSpace mColorSpace; + private int mInternalReferences; + + /** This snapshot object is being broadcast. */ + public static final int REFERENCE_BROADCAST = 1; + /** This snapshot object is in the cache. */ + public static final int REFERENCE_CACHE = 1 << 1; + /** This snapshot object is being persistent. */ + public static final int REFERENCE_PERSIST = 1 << 2; + @IntDef(flag = true, prefix = { "REFERENCE_" }, value = { + REFERENCE_BROADCAST, + REFERENCE_CACHE, + REFERENCE_PERSIST + }) + @Retention(RetentionPolicy.SOURCE) + @interface ReferenceFlags {} public TaskSnapshot(long id, long captureTime, @NonNull ComponentName topActivityComponent, HardwareBuffer snapshot, @@ -296,7 +315,28 @@ public class TaskSnapshot implements Parcelable { + " mWindowingMode=" + mWindowingMode + " mAppearance=" + mAppearance + " mIsTranslucent=" + mIsTranslucent - + " mHasImeSurface=" + mHasImeSurface; + + " mHasImeSurface=" + mHasImeSurface + + " mInternalReferences=" + mInternalReferences; + } + + /** + * Adds a reference when the object is held somewhere. + * Only used in core. + */ + public synchronized void addReference(@ReferenceFlags int usage) { + mInternalReferences |= usage; + } + + /** + * Removes a reference when the object is not held from somewhere. The snapshot will be closed + * once the reference becomes zero. + * Only used in core. + */ + public synchronized void removeReference(@ReferenceFlags int usage) { + mInternalReferences &= ~usage; + if (mInternalReferences == 0 && mSnapshot != null && !mSnapshot.isClosed()) { + mSnapshot.close(); + } } public static final @NonNull Creator<TaskSnapshot> CREATOR = new Creator<TaskSnapshot>() { diff --git a/services/core/java/com/android/server/wm/ActivitySnapshotCache.java b/services/core/java/com/android/server/wm/ActivitySnapshotCache.java index 3609837f417b..ed07afd2eab5 100644 --- a/services/core/java/com/android/server/wm/ActivitySnapshotCache.java +++ b/services/core/java/com/android/server/wm/ActivitySnapshotCache.java @@ -30,10 +30,12 @@ class ActivitySnapshotCache extends SnapshotCache<ActivityRecord> { @Override void putSnapshot(ActivityRecord ar, TaskSnapshot snapshot) { final int hasCode = System.identityHashCode(ar); + snapshot.addReference(TaskSnapshot.REFERENCE_CACHE); synchronized (mLock) { final CacheEntry entry = mRunningCache.get(hasCode); if (entry != null) { mAppIdMap.remove(entry.topApp); + entry.snapshot.removeReference(TaskSnapshot.REFERENCE_CACHE); } mAppIdMap.put(ar, hasCode); mRunningCache.put(hasCode, new CacheEntry(snapshot, ar)); diff --git a/services/core/java/com/android/server/wm/SnapshotCache.java b/services/core/java/com/android/server/wm/SnapshotCache.java index 86804360f6f4..1e6ee7dc318f 100644 --- a/services/core/java/com/android/server/wm/SnapshotCache.java +++ b/services/core/java/com/android/server/wm/SnapshotCache.java @@ -92,6 +92,7 @@ abstract class SnapshotCache<TYPE extends WindowContainer> { if (entry != null) { mAppIdMap.remove(entry.topApp); mRunningCache.remove(id); + entry.snapshot.removeReference(TaskSnapshot.REFERENCE_CACHE); } } } diff --git a/services/core/java/com/android/server/wm/SnapshotPersistQueue.java b/services/core/java/com/android/server/wm/SnapshotPersistQueue.java index 357897127f3a..42ca7b44287e 100644 --- a/services/core/java/com/android/server/wm/SnapshotPersistQueue.java +++ b/services/core/java/com/android/server/wm/SnapshotPersistQueue.java @@ -253,6 +253,7 @@ class SnapshotPersistQueue { PersistInfoProvider provider) { super(provider, userId); mId = id; + snapshot.addReference(TaskSnapshot.REFERENCE_PERSIST); mSnapshot = snapshot; } @@ -289,6 +290,7 @@ class SnapshotPersistQueue { if (failed) { deleteSnapshot(mId, mUserId, mPersistInfoProvider); } + mSnapshot.removeReference(TaskSnapshot.REFERENCE_PERSIST); Trace.traceEnd(TRACE_TAG_WINDOW_MANAGER); } diff --git a/services/core/java/com/android/server/wm/TaskChangeNotificationController.java b/services/core/java/com/android/server/wm/TaskChangeNotificationController.java index 21e7a8d63773..586f3c35c0c4 100644 --- a/services/core/java/com/android/server/wm/TaskChangeNotificationController.java +++ b/services/core/java/com/android/server/wm/TaskChangeNotificationController.java @@ -247,6 +247,7 @@ class TaskChangeNotificationController { break; case NOTIFY_TASK_SNAPSHOT_CHANGED_LISTENERS_MSG: forAllRemoteListeners(mNotifyTaskSnapshotChanged, msg); + ((TaskSnapshot) msg.obj).removeReference(TaskSnapshot.REFERENCE_BROADCAST); break; case NOTIFY_BACK_PRESSED_ON_TASK_ROOT: forAllRemoteListeners(mNotifyBackPressedOnTaskRoot, msg); @@ -485,6 +486,7 @@ class TaskChangeNotificationController { * Notify listeners that the snapshot of a task has changed. */ void notifyTaskSnapshotChanged(int taskId, TaskSnapshot snapshot) { + snapshot.addReference(TaskSnapshot.REFERENCE_BROADCAST); final Message msg = mHandler.obtainMessage(NOTIFY_TASK_SNAPSHOT_CHANGED_LISTENERS_MSG, taskId, 0, snapshot); forAllLocalListeners(mNotifyTaskSnapshotChanged, msg); diff --git a/services/core/java/com/android/server/wm/TaskSnapshotCache.java b/services/core/java/com/android/server/wm/TaskSnapshotCache.java index b69ac1bb2795..64b9df59990b 100644 --- a/services/core/java/com/android/server/wm/TaskSnapshotCache.java +++ b/services/core/java/com/android/server/wm/TaskSnapshotCache.java @@ -35,9 +35,11 @@ class TaskSnapshotCache extends SnapshotCache<Task> { void putSnapshot(Task task, TaskSnapshot snapshot) { synchronized (mLock) { + snapshot.addReference(TaskSnapshot.REFERENCE_CACHE); final CacheEntry entry = mRunningCache.get(task.mTaskId); if (entry != null) { mAppIdMap.remove(entry.topApp); + entry.snapshot.removeReference(TaskSnapshot.REFERENCE_CACHE); } final ActivityRecord top = task.getTopMostActivity(); mAppIdMap.put(top, task.mTaskId); |