Donate to e Foundation | Murena handsets with /e/OS | Own a part of Murena! Learn more

Commit 84fc8046 authored by Chris Li's avatar Chris Li Committed by Automerger Merge Worker
Browse files

Merge "Clean up previous DA organizer when registering" into sc-dev am: e032c8fa am: aa35c3d4

Original change: https://googleplex-android-review.googlesource.com/c/platform/frameworks/base/+/15106415

Change-Id: I5a3e2fe1bf75196a579552c33d858831b7de8b5f
parents b33c498d aa35c3d4
Loading
Loading
Loading
Loading
+59 −39
Original line number Original line Diff line number Diff line
@@ -26,6 +26,7 @@ import android.content.pm.ParceledListSlice;
import android.os.Binder;
import android.os.Binder;
import android.os.IBinder;
import android.os.IBinder;
import android.os.RemoteException;
import android.os.RemoteException;
import android.util.Slog;
import android.view.SurfaceControl;
import android.view.SurfaceControl;
import android.window.DisplayAreaAppearedInfo;
import android.window.DisplayAreaAppearedInfo;
import android.window.IDisplayAreaOrganizer;
import android.window.IDisplayAreaOrganizer;
@@ -49,7 +50,8 @@ public class DisplayAreaOrganizerController extends IDisplayAreaOrganizerControl


    final ActivityTaskManagerService mService;
    final ActivityTaskManagerService mService;
    private final WindowManagerGlobalLock mGlobalLock;
    private final WindowManagerGlobalLock mGlobalLock;
    private final HashMap<Integer, IDisplayAreaOrganizer> mOrganizersByFeatureIds = new HashMap();
    private final HashMap<Integer, DisplayAreaOrganizerState> mOrganizersByFeatureIds =
            new HashMap();


    private class DeathRecipient implements IBinder.DeathRecipient {
    private class DeathRecipient implements IBinder.DeathRecipient {
        int mFeature;
        int mFeature;
@@ -63,12 +65,41 @@ public class DisplayAreaOrganizerController extends IDisplayAreaOrganizerControl
        @Override
        @Override
        public void binderDied() {
        public void binderDied() {
            synchronized (mGlobalLock) {
            synchronized (mGlobalLock) {
                mOrganizersByFeatureIds.remove(mFeature);
                mOrganizersByFeatureIds.remove(mFeature).destroy();
                removeOrganizer(mOrganizer);
            }
            }
        }
        }
    }
    }


    private class DisplayAreaOrganizerState {
        private final IDisplayAreaOrganizer mOrganizer;
        private final DeathRecipient mDeathRecipient;

        DisplayAreaOrganizerState(IDisplayAreaOrganizer organizer, int feature) {
            mOrganizer = organizer;
            mDeathRecipient = new DeathRecipient(organizer, feature);
            try {
                organizer.asBinder().linkToDeath(mDeathRecipient, 0);
            } catch (RemoteException e) {
                // Oh well...
            }
        }

        void destroy() {
            IBinder organizerBinder = mOrganizer.asBinder();
            mService.mRootWindowContainer.forAllDisplayAreas((da) -> {
                if (da.mOrganizer != null && da.mOrganizer.asBinder().equals(organizerBinder)) {
                    if (da.isTaskDisplayArea() && da.asTaskDisplayArea().mCreatedByOrganizer) {
                        // Delete the organizer created TDA when unregister.
                        deleteTaskDisplayArea(da.asTaskDisplayArea());
                    } else {
                        da.setOrganizer(null);
                    }
                }
            });
            organizerBinder.unlinkToDeath(mDeathRecipient, 0);
        }
    }

    DisplayAreaOrganizerController(ActivityTaskManagerService atm) {
    DisplayAreaOrganizerController(ActivityTaskManagerService atm) {
        mService = atm;
        mService = atm;
        mGlobalLock = atm.mGlobalLock;
        mGlobalLock = atm.mGlobalLock;
@@ -80,7 +111,8 @@ public class DisplayAreaOrganizerController extends IDisplayAreaOrganizerControl


    @Nullable
    @Nullable
    IDisplayAreaOrganizer getOrganizerByFeature(int featureId) {
    IDisplayAreaOrganizer getOrganizerByFeature(int featureId) {
        return mOrganizersByFeatureIds.get(featureId);
        final DisplayAreaOrganizerState state = mOrganizersByFeatureIds.get(featureId);
        return state != null ? state.mOrganizer : null;
    }
    }


    @Override
    @Override
@@ -94,17 +126,18 @@ public class DisplayAreaOrganizerController extends IDisplayAreaOrganizerControl
                ProtoLog.v(WM_DEBUG_WINDOW_ORGANIZER, "Register display organizer=%s uid=%d",
                ProtoLog.v(WM_DEBUG_WINDOW_ORGANIZER, "Register display organizer=%s uid=%d",
                        organizer.asBinder(), uid);
                        organizer.asBinder(), uid);
                if (mOrganizersByFeatureIds.get(feature) != null) {
                if (mOrganizersByFeatureIds.get(feature) != null) {
                    if (mOrganizersByFeatureIds.get(feature).mOrganizer.asBinder()
                            .isBinderAlive()) {
                        throw new IllegalStateException(
                        throw new IllegalStateException(
                                "Replacing existing organizer currently unsupported");
                                "Replacing existing organizer currently unsupported");
                    }
                    }


                final DeathRecipient dr = new DeathRecipient(organizer, feature);
                    mOrganizersByFeatureIds.remove(feature).destroy();
                try {
                    Slog.d(TAG, "Replacing dead organizer for feature=" + feature);
                    organizer.asBinder().linkToDeath(dr, 0);
                } catch (RemoteException e) {
                    // Oh well...
                }
                }


                final DisplayAreaOrganizerState state = new DisplayAreaOrganizerState(organizer,
                        feature);
                final List<DisplayAreaAppearedInfo> displayAreaInfos = new ArrayList<>();
                final List<DisplayAreaAppearedInfo> displayAreaInfos = new ArrayList<>();
                mService.mRootWindowContainer.forAllDisplays(dc -> {
                mService.mRootWindowContainer.forAllDisplays(dc -> {
                    if (!dc.isTrusted()) {
                    if (!dc.isTrusted()) {
@@ -120,7 +153,7 @@ public class DisplayAreaOrganizerController extends IDisplayAreaOrganizerControl
                    });
                    });
                });
                });


                mOrganizersByFeatureIds.put(feature, organizer);
                mOrganizersByFeatureIds.put(feature, state);
                return new ParceledListSlice<>(displayAreaInfos);
                return new ParceledListSlice<>(displayAreaInfos);
            }
            }
        } finally {
        } finally {
@@ -137,9 +170,11 @@ public class DisplayAreaOrganizerController extends IDisplayAreaOrganizerControl
            synchronized (mGlobalLock) {
            synchronized (mGlobalLock) {
                ProtoLog.v(WM_DEBUG_WINDOW_ORGANIZER, "Unregister display organizer=%s uid=%d",
                ProtoLog.v(WM_DEBUG_WINDOW_ORGANIZER, "Unregister display organizer=%s uid=%d",
                        organizer.asBinder(), uid);
                        organizer.asBinder(), uid);
                mOrganizersByFeatureIds.entrySet().removeIf(
                mOrganizersByFeatureIds.values().forEach((state) -> {
                        entry -> entry.getValue().asBinder() == organizer.asBinder());
                    if (state.mOrganizer.asBinder() == organizer.asBinder()) {
                removeOrganizer(organizer);
                        state.destroy();
                    }
                });
            }
            }
        } finally {
        } finally {
            Binder.restoreCallingIdentity(origId);
            Binder.restoreCallingIdentity(origId);
@@ -190,19 +225,15 @@ public class DisplayAreaOrganizerController extends IDisplayAreaOrganizerControl
                }
                }


                final int taskDisplayAreaFeatureId = mNextTaskDisplayAreaFeatureId++;
                final int taskDisplayAreaFeatureId = mNextTaskDisplayAreaFeatureId++;
                final DeathRecipient dr = new DeathRecipient(organizer, taskDisplayAreaFeatureId);
                final DisplayAreaOrganizerState state = new DisplayAreaOrganizerState(organizer,
                try {
                        taskDisplayAreaFeatureId);
                    organizer.asBinder().linkToDeath(dr, 0);
                } catch (RemoteException e) {
                    // Oh well...
                }


                final TaskDisplayArea tda = parentRoot != null
                final TaskDisplayArea tda = parentRoot != null
                        ? createTaskDisplayArea(parentRoot, name, taskDisplayAreaFeatureId)
                        ? createTaskDisplayArea(parentRoot, name, taskDisplayAreaFeatureId)
                        : createTaskDisplayArea(parentTda, name, taskDisplayAreaFeatureId);
                        : createTaskDisplayArea(parentTda, name, taskDisplayAreaFeatureId);
                final DisplayAreaAppearedInfo tdaInfo = organizeDisplayArea(organizer, tda,
                final DisplayAreaAppearedInfo tdaInfo = organizeDisplayArea(organizer, tda,
                        "DisplayAreaOrganizerController.createTaskDisplayArea");
                        "DisplayAreaOrganizerController.createTaskDisplayArea");
                mOrganizersByFeatureIds.put(taskDisplayAreaFeatureId, organizer);
                mOrganizersByFeatureIds.put(taskDisplayAreaFeatureId, state);
                return tdaInfo;
                return tdaInfo;
            }
            }
        } finally {
        } finally {
@@ -230,8 +261,7 @@ public class DisplayAreaOrganizerController extends IDisplayAreaOrganizerControl
                                    + "TaskDisplayArea=" + taskDisplayArea);
                                    + "TaskDisplayArea=" + taskDisplayArea);
                }
                }


                mOrganizersByFeatureIds.remove(taskDisplayArea.mFeatureId);
                mOrganizersByFeatureIds.remove(taskDisplayArea.mFeatureId).destroy();
                deleteTaskDisplayArea(taskDisplayArea);
            }
            }
        } finally {
        } finally {
            Binder.restoreCallingIdentity(origId);
            Binder.restoreCallingIdentity(origId);
@@ -251,6 +281,10 @@ public class DisplayAreaOrganizerController extends IDisplayAreaOrganizerControl


    void onDisplayAreaVanished(IDisplayAreaOrganizer organizer, DisplayArea da) {
    void onDisplayAreaVanished(IDisplayAreaOrganizer organizer, DisplayArea da) {
        ProtoLog.v(WM_DEBUG_WINDOW_ORGANIZER, "DisplayArea vanished name=%s", da.getName());
        ProtoLog.v(WM_DEBUG_WINDOW_ORGANIZER, "DisplayArea vanished name=%s", da.getName());
        if (!organizer.asBinder().isBinderAlive()) {
            Slog.d(TAG, "Organizer died before sending onDisplayAreaVanished");
            return;
        }
        try {
        try {
            organizer.onDisplayAreaVanished(da.getDisplayAreaInfo());
            organizer.onDisplayAreaVanished(da.getDisplayAreaInfo());
        } catch (RemoteException e) {
        } catch (RemoteException e) {
@@ -267,20 +301,6 @@ public class DisplayAreaOrganizerController extends IDisplayAreaOrganizerControl
        }
        }
    }
    }


    private void removeOrganizer(IDisplayAreaOrganizer organizer) {
        IBinder organizerBinder = organizer.asBinder();
        mService.mRootWindowContainer.forAllDisplayAreas((da) -> {
            if (da.mOrganizer != null && da.mOrganizer.asBinder().equals(organizerBinder)) {
                if (da.isTaskDisplayArea() && da.asTaskDisplayArea().mCreatedByOrganizer) {
                    // Delete the organizer created TDA when unregister.
                    deleteTaskDisplayArea(da.asTaskDisplayArea());
                } else {
                    da.setOrganizer(null);
                }
            }
        });
    }

    private DisplayAreaAppearedInfo organizeDisplayArea(IDisplayAreaOrganizer organizer,
    private DisplayAreaAppearedInfo organizeDisplayArea(IDisplayAreaOrganizer organizer,
            DisplayArea displayArea, String callsite) {
            DisplayArea displayArea, String callsite) {
        displayArea.setOrganizer(organizer, true /* skipDisplayAreaAppeared */);
        displayArea.setOrganizer(organizer, true /* skipDisplayAreaAppeared */);
+2 −0
Original line number Original line Diff line number Diff line
@@ -57,6 +57,7 @@ import android.content.pm.ActivityInfo;
import android.content.res.Configuration;
import android.content.res.Configuration;
import android.graphics.Rect;
import android.graphics.Rect;
import android.os.Binder;
import android.os.Binder;
import android.os.IBinder;
import android.platform.test.annotations.Presubmit;
import android.platform.test.annotations.Presubmit;
import android.view.SurfaceControl;
import android.view.SurfaceControl;
import android.view.View;
import android.view.View;
@@ -556,6 +557,7 @@ public class DisplayAreaTest extends WindowTestsBase {
        final DisplayArea<WindowContainer> displayArea = new DisplayArea<>(
        final DisplayArea<WindowContainer> displayArea = new DisplayArea<>(
                mWm, BELOW_TASKS, "NewArea", FEATURE_VENDOR_FIRST);
                mWm, BELOW_TASKS, "NewArea", FEATURE_VENDOR_FIRST);
        final IDisplayAreaOrganizer mockDisplayAreaOrganizer = mock(IDisplayAreaOrganizer.class);
        final IDisplayAreaOrganizer mockDisplayAreaOrganizer = mock(IDisplayAreaOrganizer.class);
        doReturn(mock(IBinder.class)).when(mockDisplayAreaOrganizer).asBinder();
        displayArea.mOrganizer = mockDisplayAreaOrganizer;
        displayArea.mOrganizer = mockDisplayAreaOrganizer;
        spyOn(mWm.mAtmService.mWindowOrganizerController.mDisplayAreaOrganizerController);
        spyOn(mWm.mAtmService.mWindowOrganizerController.mDisplayAreaOrganizerController);
        mDisplayContent.addChild(displayArea, 0);
        mDisplayContent.addChild(displayArea, 0);