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

Commit 8facd571 authored by Hui Yu's avatar Hui Yu
Browse files

BG-FGS-start is allowed for companion apps.

Defined by CompanionDeviceManager.

Bug: 171305836
Test: atest cts/tests/app/src/android/app/cts/ActivityManagerFgsBgStartTest.java
Change-Id: Ia13dab3921a2c6c2e94c024bf70b8493d5eea850
parent 9cf0b739
Loading
Loading
Loading
Loading
+17 −0
Original line number Diff line number Diff line
@@ -36,6 +36,7 @@ import android.os.WorkSource;
import java.util.ArrayList;
import java.util.List;
import java.util.Map;
import java.util.Set;

/**
 * Activity manager local system service interface.
@@ -446,6 +447,22 @@ public abstract class ActivityManagerInternal {
     */
    public abstract void setDeviceOwnerUid(int uid);

    /**
     * Set all associated companion app that belongs to a userId.
     * @param userId
     * @param companionAppUids  ActivityManager will take ownership of this Set, the caller
     *                          shouldn't touch this Set after calling this interface.
     */
    public abstract void setCompanionAppUids(int userId, Set<Integer> companionAppUids);

    /**
     * is the uid an associated companion app of a userId?
     * @param userId
     * @param uid
     * @return
     */
    public abstract boolean isAssociatedCompanionApp(int userId, int uid);

    /**
     * Sends a broadcast, assuming the caller to be the system and allowing the inclusion of an
     * approved whitelist of app Ids >= {@link android.os.Process#FIRST_APPLICATION_UID} that the
+29 −19
Original line number Diff line number Diff line
@@ -33,6 +33,7 @@ import android.annotation.CheckResult;
import android.annotation.NonNull;
import android.annotation.Nullable;
import android.annotation.SuppressLint;
import android.app.ActivityManagerInternal;
import android.app.AppOpsManager;
import android.app.PendingIntent;
import android.app.role.RoleManager;
@@ -53,6 +54,7 @@ import android.content.pm.FeatureInfo;
import android.content.pm.PackageInfo;
import android.content.pm.PackageItemInfo;
import android.content.pm.PackageManager;
import android.content.pm.PackageManagerInternal;
import android.content.pm.UserInfo;
import android.net.NetworkPolicyManager;
import android.os.Binder;
@@ -111,7 +113,6 @@ import java.io.PrintWriter;
import java.nio.charset.StandardCharsets;
import java.util.ArrayList;
import java.util.Collections;
import java.util.HashSet;
import java.util.List;
import java.util.Objects;
import java.util.Set;
@@ -169,6 +170,10 @@ public class CompanionDeviceManagerService extends SystemService implements Bind
    @GuardedBy("mLock")
    private @Nullable SparseArray<Set<Association>> mCachedAssociations = new SparseArray<>();

    ActivityTaskManagerInternal mAtmInternal;
    ActivityManagerInternal mAmInternal;
    PackageManagerInternal mPackageManagerInternal;

    public CompanionDeviceManagerService(Context context) {
        super(context);
        mImpl = new CompanionDeviceManagerImpl();
@@ -176,6 +181,9 @@ public class CompanionDeviceManagerService extends SystemService implements Bind
        mRoleManager = context.getSystemService(RoleManager.class);
        mAppOpsManager = IAppOpsService.Stub.asInterface(
                ServiceManager.getService(Context.APP_OPS_SERVICE));
        mAtmInternal = LocalServices.getService(ActivityTaskManagerInternal.class);
        mAmInternal = LocalServices.getService(ActivityManagerInternal.class);
        mPackageManagerInternal = LocalServices.getService(PackageManagerInternal.class);

        Intent serviceIntent = new Intent().setComponent(SERVICE_TO_BIND_TO);
        mServiceConnectors = new PerUser<ServiceConnector<ICompanionDeviceDiscoveryService>>() {
@@ -236,15 +244,7 @@ public class CompanionDeviceManagerService extends SystemService implements Bind
        if (associations == null || associations.isEmpty()) {
            return;
        }
        Set<String> companionAppPackages = new HashSet<>();
        for (Association association : associations) {
            companionAppPackages.add(association.getPackageName());
        }
        ActivityTaskManagerInternal atmInternal = LocalServices.getService(
                ActivityTaskManagerInternal.class);
        if (atmInternal != null) {
            atmInternal.setCompanionAppPackages(userHandle, companionAppPackages);
        }
        updateAtm(userHandle, associations);

        BackgroundThread.getHandler().sendMessageDelayed(
                obtainMessage(CompanionDeviceManagerService::maybeGrantAutoRevokeExemptions, this),
@@ -727,12 +727,6 @@ public class CompanionDeviceManagerService extends SystemService implements Bind
            final Set<Association> old = getAllAssociations(userId);
            Set<Association> associations = new ArraySet<>(old);
            associations = update.apply(associations);

            Set<String> companionAppPackages = new HashSet<>();
            for (Association association : associations) {
                companionAppPackages.add(association.getPackageName());
            }

            if (DEBUG) {
                Slog.i(LOG_TAG, "Updating associations: " + old + "  -->  " + associations);
            }
@@ -741,9 +735,25 @@ public class CompanionDeviceManagerService extends SystemService implements Bind
                    CompanionDeviceManagerService::persistAssociations,
                    this, associations, userId));

            ActivityTaskManagerInternal atmInternal = LocalServices.getService(
                    ActivityTaskManagerInternal.class);
            atmInternal.setCompanionAppPackages(userId, companionAppPackages);
            updateAtm(userId, associations);
        }
    }

    private void updateAtm(int userId, Set<Association> associations) {
        final Set<Integer> companionAppUids = new ArraySet<>();
        for (Association association : associations) {
            final int uid = mPackageManagerInternal.getPackageUid(association.getPackageName(),
                    0, userId);
            if (uid >= 0) {
                companionAppUids.add(uid);
            }
        }
        if (mAtmInternal != null) {
            mAtmInternal.setCompanionAppUids(userId, companionAppUids);
        }
        if (mAmInternal != null) {
            // Make a copy of companionAppUids and send it to ActivityManager.
            mAmInternal.setCompanionAppUids(userId, new ArraySet<>(companionAppUids));
        }
    }

+13 −1
Original line number Diff line number Diff line
@@ -170,6 +170,7 @@ public final class ActiveServices {
    public static final int FGS_FEATURE_ALLOWED_BY_PROCESS_RECORD = 19;
    public static final int FGS_FEATURE_ALLOWED_BY_EXEMPTED_PACKAGES = 20;
    public static final int FGS_FEATURE_ALLOWED_BY_ACTIVITY_STARTER = 21;
    public static final int FGS_FEATURE_ALLOWED_BY_COMPANION_APP = 22;

    @IntDef(flag = true, prefix = { "FGS_FEATURE_" }, value = {
            FGS_FEATURE_DENIED,
@@ -192,7 +193,8 @@ public final class ActiveServices {
            FGS_FEATURE_ALLOWED_BY_DEVICE_DEMO_MODE,
            FGS_FEATURE_ALLOWED_BY_PROCESS_RECORD,
            FGS_FEATURE_ALLOWED_BY_EXEMPTED_PACKAGES,
            FGS_FEATURE_ALLOWED_BY_ACTIVITY_STARTER
            FGS_FEATURE_ALLOWED_BY_ACTIVITY_STARTER,
            FGS_FEATURE_ALLOWED_BY_COMPANION_APP
    })
    @Retention(RetentionPolicy.SOURCE)
    public @interface FgsFeatureRetCode {}
@@ -5379,6 +5381,14 @@ public final class ActiveServices {
            }
        }

        if (ret == FGS_FEATURE_DENIED) {
            final boolean isCompanionApp = mAm.mInternal.isAssociatedCompanionApp(
                    UserHandle.getUserId(callingUid), callingUid);
            if (isCompanionApp) {
                ret = FGS_FEATURE_ALLOWED_BY_COMPANION_APP;
            }
        }

        final String debugInfo =
                "[callingPackage: " + callingPackage
                        + "; callingUid: " + callingUid
@@ -5462,6 +5472,8 @@ public final class ActiveServices {
                return "FGS_FEATURE_ALLOWED_BY_EXEMPTED_PACKAGES";
            case FGS_FEATURE_ALLOWED_BY_ACTIVITY_STARTER:
                return "ALLOWED_BY_ACTIVITY_STARTER";
            case FGS_FEATURE_ALLOWED_BY_COMPANION_APP:
                return "ALLOWED_BY_COMPANION_APP";
            default:
                return "";
        }
+19 −0
Original line number Diff line number Diff line
@@ -573,6 +573,9 @@ public class ActivityManagerService extends IActivityManager.Stub
    private int mDeviceOwnerUid = Process.INVALID_UID;
    // A map userId and all its companion app uids
    private final Map<Integer, Set<Integer>> mCompanionAppUidsMap = new ArrayMap<>();
    final UserController mUserController;
    @VisibleForTesting
    public final PendingIntentController mPendingIntentController;
@@ -16783,6 +16786,22 @@ public class ActivityManagerService extends IActivityManager.Stub
            }
        }
        @Override
        public void setCompanionAppUids(int userId, Set<Integer> companionAppUids) {
            synchronized (ActivityManagerService.this) {
                mCompanionAppUidsMap.put(userId, companionAppUids);
            }
        }
        @Override
        public boolean isAssociatedCompanionApp(int userId, int uid) {
            final Set<Integer> allUids = mCompanionAppUidsMap.get(userId);
            if (allUids == null) {
                return false;
            }
            return allUids.contains(uid);
        }
        @Override
        public void addPendingTopUid(int uid, int pid) {
                mPendingStartActivityUids.add(uid, pid);
+7 −0
Original line number Diff line number Diff line
@@ -2068,6 +2068,13 @@ class ProcessRecord implements WindowProcessListener {
            }
        }

        if (!mAllowStartFgs) {
            if (mService.mInternal != null) {
                mAllowStartFgs = mService.mInternal.isAssociatedCompanionApp(
                        UserHandle.getUserId(info.uid), info.uid);
            }
        }

        if (!mAllowStartFgs) {
            // uid is on DeviceIdleController's user/system allowlist
            // or AMS's FgsStartTempAllowList.
Loading