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

Commit 03b6c092 authored by Evan Severson's avatar Evan Severson
Browse files

Show mic/cam enable dialog for IME

If the IME is bound with capabilities it is considered to be in use by
the user so when they attempt to open the mic or camera we show the
dialog to renable.

Test: Disable microphone and use gboard
Bug: 187154145
Change-Id: Icf8d91f2a2b97068852c1b98d36916c07c42d3fa
parent d616f1ed
Loading
Loading
Loading
Loading
+6 −0
Original line number Diff line number Diff line
@@ -19,6 +19,7 @@ package android.app;
import android.annotation.NonNull;
import android.annotation.Nullable;
import android.annotation.UserIdInt;
import android.app.ActivityManager.ProcessCapability;
import android.content.ComponentName;
import android.content.IIntentReceiver;
import android.content.IIntentSender;
@@ -634,4 +635,9 @@ public abstract class ActivityManagerInternal {
     * Return the temp allowlist type when server push messaging is over the quota.
     */
    public abstract @TempAllowListType int getPushMessagingOverQuotaBehavior();

    /**
     * Returns the capability of the given uid
     */
    public abstract @ProcessCapability int getUidCapability(int uid);
}
+32 −4
Original line number Diff line number Diff line
@@ -17,6 +17,8 @@
package com.android.server;

import static android.Manifest.permission.MANAGE_SENSOR_PRIVACY;
import static android.app.ActivityManager.PROCESS_CAPABILITY_FOREGROUND_CAMERA;
import static android.app.ActivityManager.PROCESS_CAPABILITY_FOREGROUND_MICROPHONE;
import static android.app.ActivityManager.RunningServiceInfo;
import static android.app.ActivityManager.RunningTaskInfo;
import static android.app.ActivityManager.getCurrentUser;
@@ -41,6 +43,7 @@ import android.annotation.NonNull;
import android.annotation.Nullable;
import android.annotation.UserIdInt;
import android.app.ActivityManager;
import android.app.ActivityManagerInternal;
import android.app.ActivityOptions;
import android.app.ActivityTaskManager;
import android.app.AppOpsManager;
@@ -83,6 +86,7 @@ import android.telephony.TelephonyCallback;
import android.telephony.TelephonyManager;
import android.telephony.emergency.EmergencyNumber;
import android.text.Html;
import android.text.TextUtils;
import android.util.ArrayMap;
import android.util.ArraySet;
import android.util.AtomicFile;
@@ -156,6 +160,7 @@ public final class SensorPrivacyService extends SystemService {
    private final SensorPrivacyServiceImpl mSensorPrivacyServiceImpl;
    private final UserManagerInternal mUserManagerInternal;
    private final ActivityManager mActivityManager;
    private final ActivityManagerInternal mActivityManagerInternal;
    private final ActivityTaskManager mActivityTaskManager;
    private final AppOpsManager mAppOpsManager;
    private final TelephonyManager mTelephonyManager;
@@ -173,6 +178,7 @@ public final class SensorPrivacyService extends SystemService {
        mAppOpsManager = context.getSystemService(AppOpsManager.class);
        mUserManagerInternal = getLocalService(UserManagerInternal.class);
        mActivityManager = context.getSystemService(ActivityManager.class);
        mActivityManagerInternal = getLocalService(ActivityManagerInternal.class);
        mActivityTaskManager = context.getSystemService(ActivityTaskManager.class);
        mTelephonyManager = context.getSystemService(TelephonyManager.class);

@@ -421,15 +427,37 @@ public final class SensorPrivacyService extends SystemService {
                }
            }

            String inputMethodComponent = Settings.Secure.getString(mContext.getContentResolver(),
                    Settings.Secure.DEFAULT_INPUT_METHOD);
            String inputMethodPackageName = null;
            if (inputMethodComponent != null) {
                inputMethodPackageName = ComponentName.unflattenFromString(
                        inputMethodComponent).getPackageName();
            }
            int capability = mActivityManagerInternal.getUidCapability(uid);

            if (sensor == MICROPHONE) {
                VoiceInteractionManagerInternal voiceInteractionManagerInternal =
                        LocalServices.getService(VoiceInteractionManagerInternal.class);

            if (sensor == MICROPHONE && voiceInteractionManagerInternal != null
                if (voiceInteractionManagerInternal != null
                        && voiceInteractionManagerInternal.hasActiveSession(packageName)) {
                    enqueueSensorUseReminderDialogAsync(-1, user, packageName, sensor);
                    return;
                }

                if (TextUtils.equals(packageName, inputMethodPackageName)
                        && (capability & PROCESS_CAPABILITY_FOREGROUND_MICROPHONE) != 0) {
                    enqueueSensorUseReminderDialogAsync(-1, user, packageName, sensor);
                    return;
                }
            }

            if (sensor == CAMERA && TextUtils.equals(packageName, inputMethodPackageName)
                    && (capability & PROCESS_CAPABILITY_FOREGROUND_CAMERA) != 0) {
                enqueueSensorUseReminderDialogAsync(-1, user, packageName, sensor);
                return;
            }

            Log.i(TAG, packageName + "/" + uid + " started using sensor " + sensor
                    + " but no activity or foreground service was running. The user will not be"
                    + " informed. System components should check if sensor privacy is enabled for"
+11 −0
Original line number Diff line number Diff line
@@ -16323,6 +16323,17 @@ public class ActivityManagerService extends IActivityManager.Stub
                return mConstants.mPushMessagingOverQuotaBehavior;
            }
        }
        @Override
        public int getUidCapability(int uid) {
            synchronized (ActivityManagerService.this) {
                UidRecord uidRecord = mProcessList.getUidRecordLOSP(uid);
                if (uidRecord == null) {
                    throw new IllegalArgumentException("uid record for " + uid + " not found");
                }
                return uidRecord.getCurCapability();
            }
        }
    }
    long inputDispatchingTimedOut(int pid, final boolean aboveSystem, String reason) {