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

Commit 5e880217 authored by Julia Reynolds's avatar Julia Reynolds Committed by Android (Google) Code Review
Browse files

Merge "Check that an app still has access while rebinding" into tm-qpr-dev

parents ce7b6c61 5051dd69
Loading
Loading
Loading
Loading
+13 −6
Original line number Diff line number Diff line
@@ -1447,6 +1447,16 @@ abstract public class ManagedServices {
        }
    }

    @VisibleForTesting
    void reregisterService(final ComponentName cn, final int userId) {
        // If rebinding a package that died, ensure it still has permission
        // after the rebind delay
        if (isPackageOrComponentAllowed(cn.getPackageName(), userId)
                || isPackageOrComponentAllowed(cn.flattenToString(), userId)) {
            registerService(cn, userId);
        }
    }

    /**
     * Inject a system service into the management list.
     */
@@ -1545,12 +1555,9 @@ abstract public class ManagedServices {
                        unbindService(this, name, userid);
                        if (!mServicesRebinding.contains(servicesBindingTag)) {
                            mServicesRebinding.add(servicesBindingTag);
                            mHandler.postDelayed(new Runnable() {
                                    @Override
                                    public void run() {
                                        registerService(name, userid);
                                    }
                               }, ON_BINDING_DIED_REBIND_DELAY_MS);
                            mHandler.postDelayed(() ->
                                    reregisterService(name, userid),
                                    ON_BINDING_DIED_REBIND_DELAY_MS);
                        } else {
                            Slog.v(TAG, getCaption() + " not rebinding in user " + userid
                                    + " as a previous rebind attempt was made: " + name);
+150 −0
Original line number Diff line number Diff line
@@ -839,6 +839,156 @@ public class ManagedServicesTest extends UiServiceTestCase {
        verifyExpectedBoundEntries(service, false);
    }

    @Test
    public void reregisterService_checksAppIsApproved_pkg() throws Exception {
        Context context = mock(Context.class);
        PackageManager pm = mock(PackageManager.class);
        ApplicationInfo ai = new ApplicationInfo();
        ai.targetSdkVersion = Build.VERSION_CODES.CUR_DEVELOPMENT;

        when(context.getPackageName()).thenReturn(mContext.getPackageName());
        when(context.getUserId()).thenReturn(mContext.getUserId());
        when(context.getPackageManager()).thenReturn(pm);
        when(pm.getApplicationInfo(anyString(), anyInt())).thenReturn(ai);

        ManagedServices service = new TestManagedServices(context, mLock, mUserProfiles, mIpm,
                APPROVAL_BY_PACKAGE);
        ComponentName cn = ComponentName.unflattenFromString("a/a");

        when(context.bindServiceAsUser(any(), any(), anyInt(), any())).thenAnswer(invocation -> {
            Object[] args = invocation.getArguments();
            ServiceConnection sc = (ServiceConnection) args[1];
            sc.onServiceConnected(cn, mock(IBinder.class));
            return true;
        });

        service.addApprovedList("a", 0, true);

        service.reregisterService(cn, 0);

        assertTrue(service.isBound(cn, 0));
    }

    @Test
    public void reregisterService_checksAppIsApproved_pkg_secondary() throws Exception {
        Context context = mock(Context.class);
        PackageManager pm = mock(PackageManager.class);
        ApplicationInfo ai = new ApplicationInfo();
        ai.targetSdkVersion = Build.VERSION_CODES.CUR_DEVELOPMENT;

        when(context.getPackageName()).thenReturn(mContext.getPackageName());
        when(context.getUserId()).thenReturn(mContext.getUserId());
        when(context.getPackageManager()).thenReturn(pm);
        when(pm.getApplicationInfo(anyString(), anyInt())).thenReturn(ai);

        ManagedServices service = new TestManagedServices(context, mLock, mUserProfiles, mIpm,
                APPROVAL_BY_PACKAGE);
        ComponentName cn = ComponentName.unflattenFromString("a/a");

        when(context.bindServiceAsUser(any(), any(), anyInt(), any())).thenAnswer(invocation -> {
            Object[] args = invocation.getArguments();
            ServiceConnection sc = (ServiceConnection) args[1];
            sc.onServiceConnected(cn, mock(IBinder.class));
            return true;
        });

        service.addApprovedList("a", 0, false);

        service.reregisterService(cn, 0);

        assertTrue(service.isBound(cn, 0));
    }

    @Test
    public void reregisterService_checksAppIsApproved_cn() throws Exception {
        Context context = mock(Context.class);
        PackageManager pm = mock(PackageManager.class);
        ApplicationInfo ai = new ApplicationInfo();
        ai.targetSdkVersion = Build.VERSION_CODES.CUR_DEVELOPMENT;

        when(context.getPackageName()).thenReturn(mContext.getPackageName());
        when(context.getUserId()).thenReturn(mContext.getUserId());
        when(context.getPackageManager()).thenReturn(pm);
        when(pm.getApplicationInfo(anyString(), anyInt())).thenReturn(ai);

        ManagedServices service = new TestManagedServices(context, mLock, mUserProfiles, mIpm,
                APPROVAL_BY_COMPONENT);
        ComponentName cn = ComponentName.unflattenFromString("a/a");

        when(context.bindServiceAsUser(any(), any(), anyInt(), any())).thenAnswer(invocation -> {
            Object[] args = invocation.getArguments();
            ServiceConnection sc = (ServiceConnection) args[1];
            sc.onServiceConnected(cn, mock(IBinder.class));
            return true;
        });

        service.addApprovedList("a/a", 0, true);

        service.reregisterService(cn, 0);

        assertTrue(service.isBound(cn, 0));
    }

    @Test
    public void reregisterService_checksAppIsApproved_cn_secondary() throws Exception {
        Context context = mock(Context.class);
        PackageManager pm = mock(PackageManager.class);
        ApplicationInfo ai = new ApplicationInfo();
        ai.targetSdkVersion = Build.VERSION_CODES.CUR_DEVELOPMENT;

        when(context.getPackageName()).thenReturn(mContext.getPackageName());
        when(context.getUserId()).thenReturn(mContext.getUserId());
        when(context.getPackageManager()).thenReturn(pm);
        when(pm.getApplicationInfo(anyString(), anyInt())).thenReturn(ai);

        ManagedServices service = new TestManagedServices(context, mLock, mUserProfiles, mIpm,
                APPROVAL_BY_COMPONENT);
        ComponentName cn = ComponentName.unflattenFromString("a/a");

        when(context.bindServiceAsUser(any(), any(), anyInt(), any())).thenAnswer(invocation -> {
            Object[] args = invocation.getArguments();
            ServiceConnection sc = (ServiceConnection) args[1];
            sc.onServiceConnected(cn, mock(IBinder.class));
            return true;
        });

        service.addApprovedList("a/a", 0, false);

        service.reregisterService(cn, 0);

        assertTrue(service.isBound(cn, 0));
    }

    @Test
    public void reregisterService_checksAppIsNotApproved_cn_secondary() throws Exception {
        Context context = mock(Context.class);
        PackageManager pm = mock(PackageManager.class);
        ApplicationInfo ai = new ApplicationInfo();
        ai.targetSdkVersion = Build.VERSION_CODES.CUR_DEVELOPMENT;

        when(context.getPackageName()).thenReturn(mContext.getPackageName());
        when(context.getUserId()).thenReturn(mContext.getUserId());
        when(context.getPackageManager()).thenReturn(pm);
        when(pm.getApplicationInfo(anyString(), anyInt())).thenReturn(ai);

        ManagedServices service = new TestManagedServices(context, mLock, mUserProfiles, mIpm,
                APPROVAL_BY_COMPONENT);
        ComponentName cn = ComponentName.unflattenFromString("a/a");

        when(context.bindServiceAsUser(any(), any(), anyInt(), any())).thenAnswer(invocation -> {
            Object[] args = invocation.getArguments();
            ServiceConnection sc = (ServiceConnection) args[1];
            sc.onServiceConnected(cn, mock(IBinder.class));
            return true;
        });

        service.addApprovedList("b/b", 0, false);

        service.reregisterService(cn, 0);

        assertFalse(service.isBound(cn, 0));
    }

    @Test
    public void unbindOtherUserServices() throws PackageManager.NameNotFoundException {
        Context context = mock(Context.class);