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

Commit 1371c57f authored by Riddle Hsu's avatar Riddle Hsu
Browse files

Ensure clearCallingIdentity for getDisplayContentOrCreate

If a new display is created, it may acquire wakelock for freezing
display when configuring the display. That may raise an exception
that the calling uid is not the same as the owner uid.

Fix: 147778342
Test: atest DisplayPolicyTests
Change-Id: Ib31c0d1f98964874a0ab97725d43f6bbd009062c
parent ca8106f2
Loading
Loading
Loading
Loading
+15 −14
Original line number Diff line number Diff line
@@ -937,17 +937,17 @@ public class DisplayPolicy {
     * @return If ok, WindowManagerImpl.ADD_OKAY.  If too many singletons,
     * WindowManagerImpl.ADD_MULTIPLE_SINGLETON
     */
    int validateAddingWindowLw(WindowManager.LayoutParams attrs) {
    int validateAddingWindowLw(WindowManager.LayoutParams attrs, int callingPid, int callingUid) {
        if ((attrs.privateFlags & PRIVATE_FLAG_IS_SCREEN_DECOR) != 0) {
            mContext.enforceCallingOrSelfPermission(
                    android.Manifest.permission.STATUS_BAR_SERVICE,
            mContext.enforcePermission(
                    android.Manifest.permission.STATUS_BAR_SERVICE, callingPid, callingUid,
                    "DisplayPolicy");
        }

        switch (attrs.type) {
            case TYPE_STATUS_BAR:
                mContext.enforceCallingOrSelfPermission(
                        android.Manifest.permission.STATUS_BAR_SERVICE,
                mContext.enforcePermission(
                        android.Manifest.permission.STATUS_BAR_SERVICE, callingPid, callingUid,
                        "DisplayPolicy");
                if (mStatusBar != null) {
                    if (mStatusBar.isAlive()) {
@@ -956,8 +956,8 @@ public class DisplayPolicy {
                }
                break;
            case TYPE_NOTIFICATION_SHADE:
                mContext.enforceCallingOrSelfPermission(
                        android.Manifest.permission.STATUS_BAR_SERVICE,
                mContext.enforcePermission(
                        android.Manifest.permission.STATUS_BAR_SERVICE, callingPid, callingUid,
                        "DisplayPolicy");
                if (mNotificationShade != null) {
                    if (mNotificationShade.isAlive()) {
@@ -966,8 +966,8 @@ public class DisplayPolicy {
                }
                break;
            case TYPE_NAVIGATION_BAR:
                mContext.enforceCallingOrSelfPermission(
                        android.Manifest.permission.STATUS_BAR_SERVICE,
                mContext.enforcePermission(
                        android.Manifest.permission.STATUS_BAR_SERVICE, callingPid, callingUid,
                        "DisplayPolicy");
                if (mNavigationBar != null) {
                    if (mNavigationBar.isAlive()) {
@@ -977,16 +977,17 @@ public class DisplayPolicy {
                break;
            case TYPE_NAVIGATION_BAR_PANEL:
                // Check for permission if the caller is not the recents component.
                if (!mService.mAtmInternal.isCallerRecents(Binder.getCallingUid())) {
                    mContext.enforceCallingOrSelfPermission(
                            android.Manifest.permission.STATUS_BAR_SERVICE, "DisplayPolicy");
                if (!mService.mAtmInternal.isCallerRecents(callingUid)) {
                    mContext.enforcePermission(
                            android.Manifest.permission.STATUS_BAR_SERVICE, callingPid, callingUid,
                            "DisplayPolicy");
                }
                break;
            case TYPE_STATUS_BAR_PANEL:
            case TYPE_STATUS_BAR_SUB_PANEL:
            case TYPE_VOICE_INTERACTION_STARTING:
                mContext.enforceCallingOrSelfPermission(
                        android.Manifest.permission.STATUS_BAR_SERVICE,
                mContext.enforcePermission(
                        android.Manifest.permission.STATUS_BAR_SERVICE, callingPid, callingUid,
                        "DisplayPolicy");
                break;
        }
+70 −63
Original line number Diff line number Diff line
@@ -1342,8 +1342,9 @@ public class WindowManagerService extends IWindowManager.Stub
        }

        WindowState parentWindow = null;
        long origId;
        final int callingUid = Binder.getCallingUid();
        final int callingPid = Binder.getCallingPid();
        final long origId = Binder.clearCallingIdentity();
        final int type = attrs.type;

        synchronized (mGlobalLock) {
@@ -1504,10 +1505,9 @@ public class WindowManagerService extends IWindowManager.Stub
            }

            final DisplayPolicy displayPolicy = displayContent.getDisplayPolicy();
            displayPolicy.adjustWindowParamsLw(win, win.mAttrs, Binder.getCallingPid(),
                    Binder.getCallingUid());
            displayPolicy.adjustWindowParamsLw(win, win.mAttrs, callingPid, callingUid);

            res = displayPolicy.validateAddingWindowLw(attrs);
            res = displayPolicy.validateAddingWindowLw(attrs, callingPid, callingUid);
            if (res != WindowManagerGlobal.ADD_OKAY) {
                return res;
            }
@@ -1559,8 +1559,6 @@ public class WindowManagerService extends IWindowManager.Stub
                displayContent.mTapExcludedWindows.add(win);
            }

            origId = Binder.clearCallingIdentity();

            win.attach();
            mWindowMap.put(client.asBinder(), win);
            win.initAppOpsState();
@@ -2569,10 +2567,14 @@ public class WindowManagerService extends IWindowManager.Stub
            }
        }

        final int callingUid = Binder.getCallingUid();
        final long origId = Binder.clearCallingIdentity();
        try {
            synchronized (mGlobalLock) {
                if (!callerCanManageAppTokens) {
                if (!unprivilegedAppCanCreateTokenWith(null, Binder.getCallingUid(), type, type,
                        null, packageName) || packageName == null) {
                    if (packageName == null || !unprivilegedAppCanCreateTokenWith(
                            null /* parentWindow */, callingUid, type, type, null /* tokenForLog */,
                            packageName)) {
                        throw new SecurityException("Requires MANAGE_APP_TOKENS permission");
                    }
                }
@@ -2598,6 +2600,9 @@ public class WindowManagerService extends IWindowManager.Stub
                    new WindowToken(this, binder, type, true, dc, callerCanManageAppTokens);
                }
            }
        } finally {
            Binder.restoreCallingIdentity(origId);
        }
        return WindowManagerGlobal.ADD_OKAY;
    }

@@ -6843,6 +6848,8 @@ public class WindowManagerService extends IWindowManager.Stub
            throw new SecurityException("Requires INTERNAL_SYSTEM_WINDOW permission");
        }

        final long origId = Binder.clearCallingIdentity();
        try {
            synchronized (mGlobalLock) {
                final DisplayContent displayContent = getDisplayContentOrCreate(displayId, null);
                if (displayContent == null) {
@@ -6858,20 +6865,16 @@ public class WindowManagerService extends IWindowManager.Stub
                displayContent.reconfigureDisplayLocked();

                if (lastWindowingMode != displayContent.getWindowingMode()) {
                // reconfigure won't detect this change in isolation because the windowing mode is
                // already set on the display, so fire off a new config now.

                final long origId = Binder.clearCallingIdentity();
                try {
                    // direct call since lock is shared.
                    // reconfigure won't detect this change in isolation because the windowing mode
                    // is already set on the display, so fire off a new config now.
                    displayContent.sendNewConfiguration();
                } finally {
                    Binder.restoreCallingIdentity(origId);
                }
                // Now that all configurations are updated, execute pending transitions
                    // Now that all configurations are updated, execute pending transitions.
                    displayContent.executeAppTransition();
                }
            }
        } finally {
            Binder.restoreCallingIdentity(origId);
        }
    }

    @Override
@@ -6898,6 +6901,8 @@ public class WindowManagerService extends IWindowManager.Stub
            throw new SecurityException("Requires INTERNAL_SYSTEM_WINDOW permission");
        }

        final long origId = Binder.clearCallingIdentity();
        try {
            synchronized (mGlobalLock) {
                final DisplayContent displayContent = getDisplayContentOrCreate(displayId, null);
                if (displayContent == null) {
@@ -6908,9 +6913,11 @@ public class WindowManagerService extends IWindowManager.Stub
                }

                mDisplayWindowSettings.setRemoveContentModeLocked(displayContent, mode);

                displayContent.reconfigureDisplayLocked();
            }
        } finally {
            Binder.restoreCallingIdentity(origId);
        }
    }

    @Override
+4 −3
Original line number Diff line number Diff line
@@ -102,10 +102,11 @@ public class DisplayPolicyTestsBase extends WindowTestsBase {
    }

    void addWindow(WindowState win) {
        mDisplayPolicy.adjustWindowParamsLw(win, win.mAttrs, Binder.getCallingPid(),
                Binder.getCallingUid());
        final int callingPid = Binder.getCallingPid();
        final int callingUid = Binder.getCallingUid();
        mDisplayPolicy.adjustWindowParamsLw(win, win.mAttrs, callingPid, callingUid);
        assertEquals(WindowManagerGlobal.ADD_OKAY,
                mDisplayPolicy.validateAddingWindowLw(win.mAttrs));
                mDisplayPolicy.validateAddingWindowLw(win.mAttrs, callingPid, callingUid));
        mDisplayPolicy.addWindowLw(win, win.mAttrs);
        win.mHasSurface = true;
    }