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

Commit 927fbf0f authored by Felipe Leme's avatar Felipe Leme
Browse files

Allow Intelligence Service app to obtain Clipboard permission.

Test: manual verification

Bug: 111276913
Fixes: 119440304

Change-Id: I8dc97e4517367eaf8736741ce04040efaeb84355
parent e9f5e860
Loading
Loading
Loading
Loading
+15 −6
Original line number Diff line number Diff line
@@ -55,6 +55,7 @@ import android.util.SparseArray;

import com.android.server.LocalServices;
import com.android.server.SystemService;
import com.android.server.intelligence.IntelligenceManagerInternal;
import com.android.server.uri.UriGrantsManagerInternal;
import com.android.server.wm.WindowManagerInternal;

@@ -157,6 +158,7 @@ public class ClipboardService extends SystemService {
    private final IUserManager mUm;
    private final PackageManager mPm;
    private final AppOpsManager mAppOps;
    private final IntelligenceManagerInternal mIm;
    private final IBinder mPermissionOwner;
    private HostClipboardMonitor mHostClipboardMonitor = null;
    private Thread mHostMonitorThread = null;
@@ -176,6 +178,7 @@ public class ClipboardService extends SystemService {
        mPm = getContext().getPackageManager();
        mUm = (IUserManager) ServiceManager.getService(Context.USER_SERVICE);
        mAppOps = (AppOpsManager) getContext().getSystemService(Context.APP_OPS_SERVICE);
        mIm = LocalServices.getService(IntelligenceManagerInternal.class);
        final IBinder permOwner = mUgmInternal.newUriPermissionOwner("clipboard");
        mPermissionOwner = permOwner;
        if (IS_EMULATOR) {
@@ -635,8 +638,9 @@ public class ClipboardService extends SystemService {
            return true;
        }
        // The default IME is always allowed to access the clipboard.
        int userId = UserHandle.getUserId(callingUid);
        String defaultIme = Settings.Secure.getStringForUser(getContext().getContentResolver(),
                Settings.Secure.DEFAULT_INPUT_METHOD, UserHandle.getUserId(callingUid));
                Settings.Secure.DEFAULT_INPUT_METHOD, userId);
        if (!TextUtils.isEmpty(defaultIme)) {
            final String imePkg = ComponentName.unflattenFromString(defaultIme).getPackageName();
            if (imePkg.equals(callingPackage)) {
@@ -646,13 +650,18 @@ public class ClipboardService extends SystemService {

        switch (op) {
            case AppOpsManager.OP_READ_CLIPBOARD:
                // Clipboard can only be read by applications with focus.
                boolean uidFocused = mWm.isUidFocused(callingUid);
                if (!uidFocused) {
                // Clipboard can only be read by applications with focus..
                boolean allowed = mWm.isUidFocused(callingUid);
                if (!allowed && mIm != null) {
                    // ...or the Intelligence Service
                    allowed = mIm.isIntelligenceServiceForUser(callingUid, userId);
                }
                if (!allowed) {
                    Slog.e(TAG, "Denying clipboard access to " + callingPackage
                            + ", application is not in focus.");
                            + ", application is not in focus neither is the IntelligeService for "
                            + "user " + userId);
                }
                return uidFocused;
                return allowed;
            case AppOpsManager.OP_WRITE_CLIPBOARD:
                // Writing is allowed without focus.
                return true;
+33 −0
Original line number Diff line number Diff line
/*
 * Copyright (C) 2018 The Android Open Source Project
 *
 * Licensed under the Apache License, Version 2.0 (the "License");
 * you may not use this file except in compliance with the License.
 * You may obtain a copy of the License at
 *
 *      http://www.apache.org/licenses/LICENSE-2.0
 *
 * Unless required by applicable law or agreed to in writing, software
 * distributed under the License is distributed on an "AS IS" BASIS,
 * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
 * See the License for the specific language governing permissions and
 * limitations under the License.
 */
package com.android.server.intelligence;

import android.annotation.UserIdInt;

/**
 * Intelligence Manager local system service interface.
 *
 * @hide Only for use within the system server.
 */
public abstract class IntelligenceManagerInternal {

    /**
     * Checks whether the given {@code uid} owns the
     * {@link android.service.intelligence.IntelligenceService} implementation associated with the
     * given {@code userId}.
     */
    public abstract boolean isIntelligenceServiceForUser(int uid, @UserIdInt int userId);
}
+18 −0
Original line number Diff line number Diff line
@@ -53,6 +53,8 @@ public final class IntelligenceManagerService
    @GuardedBy("mLock")
    private ActivityManagerInternal mAm;

    private final LocalService mLocalService = new LocalService();

    public IntelligenceManagerService(Context context) {
        super(context, UserManager.DISALLOW_INTELLIGENCE_CAPTURE);
    }
@@ -73,6 +75,7 @@ public final class IntelligenceManagerService
    public void onStart() {
        publishBinderService(INTELLIGENCE_MANAGER_SERVICE,
                new IntelligenceManagerServiceStub());
        publishLocalService(IntelligenceManagerInternal.class, mLocalService);
    }

    private ActivityManagerInternal getAmInternal() {
@@ -139,4 +142,19 @@ public final class IntelligenceManagerService
            }
        }
    }

    private final class LocalService extends IntelligenceManagerInternal {

        @Override
        public boolean isIntelligenceServiceForUser(int uid, int userId) {
            synchronized (mLock) {
                final IntelligencePerUserService service = peekServiceForUserLocked(userId);
                if (service != null) {
                    return service.isIntelligenceServiceForUserLocked(uid);
                }
            }

            return false;
        }
    }
}
+5 −0
Original line number Diff line number Diff line
@@ -158,6 +158,11 @@ final class IntelligencePerUserService
        mSessions.remove(sessionId);
    }

    @GuardedBy("mLock")
    public boolean isIntelligenceServiceForUserLocked(int uid) {
        return uid == getServiceUidLocked();
    }

    @Override
    protected void dumpLocked(String prefix, PrintWriter pw) {
        super.dumpLocked(prefix, pw);
+7 −6
Original line number Diff line number Diff line
@@ -1139,6 +1139,13 @@ public final class SystemServer {
                traceEnd();
            }

            if (!disableIntelligence) {
                traceBeginAndSlog("StartIntelligenceService");
                mSystemServiceManager.startService(INTELLIGENCE_MANAGER_SERVICE_CLASS);
                traceEnd();
            }

            // NOTE: ClipboardService indirectly depends on IntelligenceService
            traceBeginAndSlog("StartClipboardService");
            mSystemServiceManager.startService(ClipboardService.class);
            traceEnd();
@@ -1769,12 +1776,6 @@ public final class SystemServer {
            traceEnd();
        }

        if (!disableIntelligence) {
            traceBeginAndSlog("StartIntelligenceService");
            mSystemServiceManager.startService(INTELLIGENCE_MANAGER_SERVICE_CLASS);
            traceEnd();
        }

        traceBeginAndSlog("AppServiceManager");
        mSystemServiceManager.startService(AppBindingService.Lifecycle.class);
        traceEnd();