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

Commit c4358e4e authored by Momoko Hattori's avatar Momoko Hattori
Browse files

Refactor BackupManagerService to use UserManagerInternal

Replace the usage of the public `UserManager` API with the
internal `UserManagerInternal` service within BackupManagerService.
This aligns with common practice for core system services interacting
with user management and allows access to internal helper methods.

Also remove the unused getContext() method.

Test: atest com.android.server.backup.BackupManagerServiceTest
Test: atest com.android.server.backup.BackupManagerServiceRoboTest
Test: atest com.android.server.backup.UserBackupManagerServiceTest
Test: atest com.android.server.backup.keyvalue.KeyValueBackupTaskTest
Test: atest com.android.server.backup.internal.SetupObserverTest
Bug: 406114361
Flag: EXEMPT refactoring
Change-Id: Ia43f28c2426fc146e37dea08bb714464a2f17b93
parent 9dda8403
Loading
Loading
Loading
Loading
+13 −22
Original line number Original line Diff line number Diff line
@@ -64,6 +64,7 @@ import com.android.server.LocalServices;
import com.android.server.SystemConfig;
import com.android.server.SystemConfig;
import com.android.server.SystemService;
import com.android.server.SystemService;
import com.android.server.backup.utils.RandomAccessFileUtils;
import com.android.server.backup.utils.RandomAccessFileUtils;
import com.android.server.pm.UserManagerInternal;


import java.io.File;
import java.io.File;
import java.io.FileDescriptor;
import java.io.FileDescriptor;
@@ -129,7 +130,7 @@ public class BackupManagerService extends IBackupManager.Stub implements BackupM
    }
    }


    private final Context mContext;
    private final Context mContext;
    private final UserManager mUserManager;
    private final UserManagerInternal mUserManagerInternal;


    private final Object mLock = new Object();
    private final Object mLock = new Object();


@@ -179,14 +180,14 @@ public class BackupManagerService extends IBackupManager.Stub implements BackupM
                new HandlerThread(BACKUP_THREAD, Process.THREAD_PRIORITY_BACKGROUND);
                new HandlerThread(BACKUP_THREAD, Process.THREAD_PRIORITY_BACKGROUND);
        handlerThread.start();
        handlerThread.start();
        mHandler = new Handler(handlerThread.getLooper());
        mHandler = new Handler(handlerThread.getLooper());
        mUserManager = UserManager.get(context);
        mUserManagerInternal = LocalServices.getService(UserManagerInternal.class);
        mUserServices = new SparseArray<>();
        mUserServices = new SparseArray<>();
        Set<ComponentName> transportWhitelist =
        Set<ComponentName> transportWhitelist =
                SystemConfig.getInstance().getBackupTransportWhitelist();
                SystemConfig.getInstance().getBackupTransportWhitelist();
        mTransportWhitelist = (transportWhitelist == null) ? emptySet() : transportWhitelist;
        mTransportWhitelist = (transportWhitelist == null) ? emptySet() : transportWhitelist;
        mContext.registerReceiver(
        mContext.registerReceiver(
                mUserRemovedReceiver, new IntentFilter(Intent.ACTION_USER_REMOVED));
                mUserRemovedReceiver, new IntentFilter(Intent.ACTION_USER_REMOVED));
        mDidMainUserExistAtBoot = getUserManager().getMainUser() != null;
        mDidMainUserExistAtBoot = mUserManagerInternal.getMainUserId() != UserHandle.USER_NULL;
        if (!mDidMainUserExistAtBoot) {
        if (!mDidMainUserExistAtBoot) {
            // This might happen on the first boot if BMS starts before the main user is created.
            // This might happen on the first boot if BMS starts before the main user is created.
            Slog.d(TAG, "Main user does not exist yet");
            Slog.d(TAG, "Main user does not exist yet");
@@ -362,13 +363,13 @@ public class BackupManagerService extends IBackupManager.Stub implements BackupM
        }
        }


        // Returns false if the user is not a full user.
        // Returns false if the user is not a full user.
        if (!getUserManager().getUserInfo(userId).isFull()) {
        if (!mUserManagerInternal.getUserInfo(userId).isFull()) {
            return false;
            return false;
        }
        }


        // Returns true for the main user.
        // Returns true for the main user.
        UserHandle mainUser = getUserManager().getMainUser();
        int mainUserId = mUserManagerInternal.getMainUserId();
        if (mainUser != null && userId == mainUser.getIdentifier()) {
        if (mainUserId != UserHandle.USER_NULL && userId == mainUserId) {
            return true;
            return true;
        }
        }


@@ -376,16 +377,6 @@ public class BackupManagerService extends IBackupManager.Stub implements BackupM
        return android.multiuser.Flags.backupActivatedForAllUsers();
        return android.multiuser.Flags.backupActivatedForAllUsers();
    }
    }


    @VisibleForTesting
    protected Context getContext() {
        return mContext;
    }

    @VisibleForTesting
    protected UserManager getUserManager() {
        return mUserManager;
    }

    @VisibleForTesting
    @VisibleForTesting
    protected void postToHandler(Runnable runnable) {
    protected void postToHandler(Runnable runnable) {
        mHandler.post(runnable);
        mHandler.post(runnable);
@@ -486,7 +477,7 @@ public class BackupManagerService extends IBackupManager.Stub implements BackupM
    private void enforcePermissionsOnUser(@UserIdInt int userId) throws SecurityException {
    private void enforcePermissionsOnUser(@UserIdInt int userId) throws SecurityException {
        boolean isRestrictedUser =
        boolean isRestrictedUser =
                userId == UserHandle.USER_SYSTEM
                userId == UserHandle.USER_SYSTEM
                        || getUserManager().getUserInfo(userId).isManagedProfile();
                        || mUserManagerInternal.getUserInfo(userId).isManagedProfile();


        if (isRestrictedUser) {
        if (isRestrictedUser) {
            int caller = binderGetCallingUid();
            int caller = binderGetCallingUid();
@@ -544,7 +535,7 @@ public class BackupManagerService extends IBackupManager.Stub implements BackupM


                // If the user is unlocked, we can start the backup service for it. Otherwise we
                // If the user is unlocked, we can start the backup service for it. Otherwise we
                // will start the service when the user is unlocked as part of its unlock callback.
                // will start the service when the user is unlocked as part of its unlock callback.
                if (getUserManager().isUserUnlocked(userId)) {
                if (mUserManagerInternal.isUserUnlocked(userId)) {
                    // Clear calling identity as initialization enforces the system identity but we
                    // Clear calling identity as initialization enforces the system identity but we
                    // can be coming from shell.
                    // can be coming from shell.
                    final long oldId = Binder.clearCallingIdentity();
                    final long oldId = Binder.clearCallingIdentity();
@@ -1482,7 +1473,7 @@ public class BackupManagerService extends IBackupManager.Stub implements BackupM
        final int[] userIds;
        final int[] userIds;
        final long oldId = Binder.clearCallingIdentity();
        final long oldId = Binder.clearCallingIdentity();
        try {
        try {
            userIds = getUserManager().getProfileIds(callingUserId, false);
            userIds = mUserManagerInternal.getProfileIds(callingUserId, false);
        } finally {
        } finally {
            Binder.restoreCallingIdentity(oldId);
            Binder.restoreCallingIdentity(oldId);
        }
        }
@@ -1775,12 +1766,12 @@ public class BackupManagerService extends IBackupManager.Stub implements BackupM
            return;
            return;
        }
        }


        UserHandle mainUser = getUserManager().getMainUser();
        int mainUserId = mUserManagerInternal.getMainUserId();
        if (mainUser == null) {
        if (mainUserId == UserHandle.USER_NULL) {
            return;
            return;
        }
        }


        if (mainUser.getIdentifier() == UserHandle.USER_SYSTEM) {
        if (mainUserId == UserHandle.USER_SYSTEM) {
            return;
            return;
        }
        }


+9 −8
Original line number Original line Diff line number Diff line
@@ -49,18 +49,17 @@ import android.os.IBinder;
import android.os.ParcelFileDescriptor;
import android.os.ParcelFileDescriptor;
import android.os.Process;
import android.os.Process;
import android.os.UserHandle;
import android.os.UserHandle;
import android.os.UserManager;
import android.platform.test.annotations.Presubmit;
import android.platform.test.annotations.Presubmit;
import android.util.SparseArray;
import android.util.SparseArray;


import com.android.server.LocalServices;
import com.android.server.LocalServices;
import com.android.server.SystemService.TargetUser;
import com.android.server.SystemService.TargetUser;
import com.android.server.backup.testing.TransportData;
import com.android.server.backup.testing.TransportData;
import com.android.server.pm.UserManagerInternal;
import com.android.server.testing.shadows.ShadowApplicationPackageManager;
import com.android.server.testing.shadows.ShadowApplicationPackageManager;
import com.android.server.testing.shadows.ShadowBinder;
import com.android.server.testing.shadows.ShadowBinder;
import com.android.server.testing.shadows.ShadowEnvironment;
import com.android.server.testing.shadows.ShadowEnvironment;
import com.android.server.testing.shadows.ShadowSystemServiceRegistry;
import com.android.server.testing.shadows.ShadowSystemServiceRegistry;
import com.android.server.testing.shadows.ShadowUserManager;


import org.junit.Before;
import org.junit.Before;
import org.junit.Test;
import org.junit.Test;
@@ -70,7 +69,6 @@ import org.mockito.MockitoAnnotations;
import org.robolectric.RobolectricTestRunner;
import org.robolectric.RobolectricTestRunner;
import org.robolectric.RuntimeEnvironment;
import org.robolectric.RuntimeEnvironment;
import org.robolectric.annotation.Config;
import org.robolectric.annotation.Config;
import org.robolectric.shadow.api.Shadow;
import org.robolectric.shadows.ShadowContextWrapper;
import org.robolectric.shadows.ShadowContextWrapper;


import java.io.File;
import java.io.File;
@@ -82,7 +80,6 @@ import java.io.IOException;
        shadows = {
        shadows = {
                ShadowApplicationPackageManager.class,
                ShadowApplicationPackageManager.class,
                ShadowBinder.class,
                ShadowBinder.class,
                ShadowUserManager.class,
                ShadowEnvironment.class,
                ShadowEnvironment.class,
                ShadowSystemServiceRegistry.class
                ShadowSystemServiceRegistry.class
        })
        })
@@ -94,13 +91,14 @@ public class BackupManagerServiceRoboTest {


    private Context mContext;
    private Context mContext;
    private ShadowContextWrapper mShadowContext;
    private ShadowContextWrapper mShadowContext;
    private ShadowUserManager mShadowUserManager;
    @UserIdInt private int mUserOneId;
    @UserIdInt private int mUserOneId;
    @UserIdInt private int mUserTwoId;
    @UserIdInt private int mUserTwoId;
    @Mock private UserBackupManagerService mUserSystemService;
    @Mock private UserBackupManagerService mUserSystemService;
    @Mock private UserBackupManagerService mUserOneService;
    @Mock private UserBackupManagerService mUserOneService;
    @Mock private BackupAgentConnectionManager mUserOneBackupAgentConnectionManager;
    @Mock private BackupAgentConnectionManager mUserOneBackupAgentConnectionManager;
    @Mock private UserBackupManagerService mUserTwoService;
    @Mock private UserBackupManagerService mUserTwoService;
    @Mock private UserManagerInternal mUserManagerInternal;
    @Mock private UserInfo mUserInfoMock;


    /** Setup */
    /** Setup */
    @Before
    @Before
@@ -110,16 +108,19 @@ public class BackupManagerServiceRoboTest {
        Application application = RuntimeEnvironment.application;
        Application application = RuntimeEnvironment.application;
        mContext = application;
        mContext = application;
        mShadowContext = shadowOf(application);
        mShadowContext = shadowOf(application);
        mShadowUserManager = Shadow.extract(UserManager.get(application));


        mUserOneId = UserHandle.USER_SYSTEM + 1;
        mUserOneId = UserHandle.USER_SYSTEM + 1;
        mUserTwoId = mUserOneId + 1;
        mUserTwoId = mUserOneId + 1;
        mShadowUserManager.addUser(mUserOneId, "mUserOneId", 0);
        mShadowUserManager.addUser(mUserTwoId, "mUserTwoId", 0);


        mShadowContext.grantPermissions(BACKUP);
        mShadowContext.grantPermissions(BACKUP);
        mShadowContext.grantPermissions(INTERACT_ACROSS_USERS_FULL);
        mShadowContext.grantPermissions(INTERACT_ACROSS_USERS_FULL);


        LocalServices.removeServiceForTest(UserManagerInternal.class);
        LocalServices.addService(UserManagerInternal.class, mUserManagerInternal);

        when(mUserManagerInternal.getUserInfo(mUserOneId)).thenReturn(mUserInfoMock);
        when(mUserManagerInternal.getUserInfo(mUserTwoId)).thenReturn(mUserInfoMock);

        when(mUserOneService.getBackupAgentConnectionManager()).thenReturn(
        when(mUserOneService.getBackupAgentConnectionManager()).thenReturn(
                mUserOneBackupAgentConnectionManager);
                mUserOneBackupAgentConnectionManager);


+6 −2
Original line number Original line Diff line number Diff line
@@ -54,17 +54,18 @@ import android.os.UserHandle;
import android.platform.test.annotations.Presubmit;
import android.platform.test.annotations.Presubmit;
import android.provider.Settings;
import android.provider.Settings;


import com.android.server.LocalServices;
import com.android.server.backup.testing.BackupManagerServiceTestUtils;
import com.android.server.backup.testing.BackupManagerServiceTestUtils;
import com.android.server.backup.testing.TransportData;
import com.android.server.backup.testing.TransportData;
import com.android.server.backup.testing.TransportTestUtils.TransportMock;
import com.android.server.backup.testing.TransportTestUtils.TransportMock;
import com.android.server.backup.transport.TransportNotRegisteredException;
import com.android.server.backup.transport.TransportNotRegisteredException;
import com.android.server.pm.UserManagerInternal;
import com.android.server.testing.shadows.ShadowApplicationPackageManager;
import com.android.server.testing.shadows.ShadowApplicationPackageManager;
import com.android.server.testing.shadows.ShadowBackupEligibilityRules;
import com.android.server.testing.shadows.ShadowBackupEligibilityRules;
import com.android.server.testing.shadows.ShadowBinder;
import com.android.server.testing.shadows.ShadowBinder;
import com.android.server.testing.shadows.ShadowKeyValueBackupJob;
import com.android.server.testing.shadows.ShadowKeyValueBackupJob;
import com.android.server.testing.shadows.ShadowKeyValueBackupTask;
import com.android.server.testing.shadows.ShadowKeyValueBackupTask;
import com.android.server.testing.shadows.ShadowSystemServiceRegistry;
import com.android.server.testing.shadows.ShadowSystemServiceRegistry;
import com.android.server.testing.shadows.ShadowUserManager;


import org.junit.After;
import org.junit.After;
import org.junit.Before;
import org.junit.Before;
@@ -99,7 +100,6 @@ import java.util.List;
            ShadowBackupEligibilityRules.class,
            ShadowBackupEligibilityRules.class,
            ShadowApplicationPackageManager.class,
            ShadowApplicationPackageManager.class,
            ShadowSystemServiceRegistry.class,
            ShadowSystemServiceRegistry.class,
            ShadowUserManager.class
        })
        })
@Presubmit
@Presubmit
public class UserBackupManagerServiceTest {
public class UserBackupManagerServiceTest {
@@ -109,6 +109,7 @@ public class UserBackupManagerServiceTest {
    private static final int USER_ID = 10;
    private static final int USER_ID = 10;


    @Mock private TransportManager mTransportManager;
    @Mock private TransportManager mTransportManager;
    @Mock private UserManagerInternal mUserManagerInternal;
    private HandlerThread mBackupThread;
    private HandlerThread mBackupThread;
    private ShadowLooper mShadowBackupLooper;
    private ShadowLooper mShadowBackupLooper;
    private File mBaseStateDir;
    private File mBaseStateDir;
@@ -142,6 +143,9 @@ public class UserBackupManagerServiceTest {
        mContext = context;
        mContext = context;
        mShadowContext = shadowOf(context);
        mShadowContext = shadowOf(context);


        LocalServices.removeServiceForTest(UserManagerInternal.class);
        LocalServices.addService(UserManagerInternal.class, mUserManagerInternal);

        File cacheDir = mContext.getCacheDir();
        File cacheDir = mContext.getCacheDir();
        // Corresponds to /data/backup
        // Corresponds to /data/backup
        mBaseStateDir = new File(cacheDir, "base_state");
        mBaseStateDir = new File(cacheDir, "base_state");
+5 −2
Original line number Original line Diff line number Diff line
@@ -25,15 +25,16 @@ import android.os.HandlerThread;
import android.platform.test.annotations.Presubmit;
import android.platform.test.annotations.Presubmit;
import android.provider.Settings;
import android.provider.Settings;


import com.android.server.LocalServices;
import com.android.server.backup.FullBackupJob;
import com.android.server.backup.FullBackupJob;
import com.android.server.backup.JobIdManager;
import com.android.server.backup.JobIdManager;
import com.android.server.backup.KeyValueBackupJob;
import com.android.server.backup.KeyValueBackupJob;
import com.android.server.backup.TransportManager;
import com.android.server.backup.TransportManager;
import com.android.server.backup.UserBackupManagerService;
import com.android.server.backup.UserBackupManagerService;
import com.android.server.backup.testing.BackupManagerServiceTestUtils;
import com.android.server.backup.testing.BackupManagerServiceTestUtils;
import com.android.server.pm.UserManagerInternal;
import com.android.server.testing.shadows.ShadowApplicationPackageManager;
import com.android.server.testing.shadows.ShadowApplicationPackageManager;
import com.android.server.testing.shadows.ShadowSystemServiceRegistry;
import com.android.server.testing.shadows.ShadowSystemServiceRegistry;
import com.android.server.testing.shadows.ShadowUserManager;


import org.junit.Before;
import org.junit.Before;
import org.junit.Test;
import org.junit.Test;
@@ -58,7 +59,6 @@ import java.io.File;
            ShadowApplicationPackageManager.class,
            ShadowApplicationPackageManager.class,
            ShadowJobScheduler.class,
            ShadowJobScheduler.class,
            ShadowSystemServiceRegistry.class,
            ShadowSystemServiceRegistry.class,
            ShadowUserManager.class
        })
        })
@Presubmit
@Presubmit
public class SetupObserverTest {
public class SetupObserverTest {
@@ -66,6 +66,7 @@ public class SetupObserverTest {
    private static final int USER_ID = 10;
    private static final int USER_ID = 10;


    @Mock private TransportManager mTransportManager;
    @Mock private TransportManager mTransportManager;
    @Mock private UserManagerInternal mUserManagerInternal;


    private Context mContext;
    private Context mContext;
    private UserBackupManagerService mUserBackupManagerService;
    private UserBackupManagerService mUserBackupManagerService;
@@ -76,6 +77,8 @@ public class SetupObserverTest {
    @Before
    @Before
    public void setUp() throws Exception {
    public void setUp() throws Exception {
        MockitoAnnotations.initMocks(this);
        MockitoAnnotations.initMocks(this);
        LocalServices.removeServiceForTest(UserManagerInternal.class);
        LocalServices.addService(UserManagerInternal.class, mUserManagerInternal);
        mContext = RuntimeEnvironment.application;
        mContext = RuntimeEnvironment.application;
        mHandlerThread = BackupManagerServiceTestUtils.startSilentBackupThread(TAG);
        mHandlerThread = BackupManagerServiceTestUtils.startSilentBackupThread(TAG);
        mUserBackupManagerService =
        mUserBackupManagerService =
+5 −2
Original line number Original line Diff line number Diff line
@@ -126,13 +126,13 @@ import com.android.server.backup.testing.TransportTestUtils;
import com.android.server.backup.testing.TransportTestUtils.TransportMock;
import com.android.server.backup.testing.TransportTestUtils.TransportMock;
import com.android.server.backup.utils.BackupEligibilityRules;
import com.android.server.backup.utils.BackupEligibilityRules;
import com.android.server.backup.utils.BackupManagerMonitorEventSender;
import com.android.server.backup.utils.BackupManagerMonitorEventSender;
import com.android.server.pm.UserManagerInternal;
import com.android.server.testing.shadows.FrameworkShadowLooper;
import com.android.server.testing.shadows.FrameworkShadowLooper;
import com.android.server.testing.shadows.ShadowApplicationPackageManager;
import com.android.server.testing.shadows.ShadowApplicationPackageManager;
import com.android.server.testing.shadows.ShadowBackupDataInput;
import com.android.server.testing.shadows.ShadowBackupDataInput;
import com.android.server.testing.shadows.ShadowBackupDataOutput;
import com.android.server.testing.shadows.ShadowBackupDataOutput;
import com.android.server.testing.shadows.ShadowEventLog;
import com.android.server.testing.shadows.ShadowEventLog;
import com.android.server.testing.shadows.ShadowSystemServiceRegistry;
import com.android.server.testing.shadows.ShadowSystemServiceRegistry;
import com.android.server.testing.shadows.ShadowUserManager;


import com.google.common.base.Charsets;
import com.google.common.base.Charsets;
import com.google.common.truth.IterableSubject;
import com.google.common.truth.IterableSubject;
@@ -180,7 +180,6 @@ import java.util.stream.Stream;
            ShadowEventLog.class,
            ShadowEventLog.class,
            ShadowQueuedWork.class,
            ShadowQueuedWork.class,
            ShadowSystemServiceRegistry.class,
            ShadowSystemServiceRegistry.class,
            ShadowUserManager.class
        })
        })
@Presubmit
@Presubmit
public class KeyValueBackupTaskTest  {
public class KeyValueBackupTaskTest  {
@@ -198,6 +197,7 @@ public class KeyValueBackupTaskTest {
    @Mock private OnTaskFinishedListener mListener;
    @Mock private OnTaskFinishedListener mListener;
    @Mock private PackageManagerInternal mPackageManagerInternal;
    @Mock private PackageManagerInternal mPackageManagerInternal;
    @Mock private BackupAgentConnectionManager mBackupAgentConnectionManager;
    @Mock private BackupAgentConnectionManager mBackupAgentConnectionManager;
    @Mock private UserManagerInternal mUserManagerInternal;


    private UserBackupManagerService mBackupManagerService;
    private UserBackupManagerService mBackupManagerService;
    private TransportData mTransport;
    private TransportData mTransport;
@@ -243,6 +243,9 @@ public class KeyValueBackupTaskTest {
        mWakeLock = spy(createBackupWakeLock(mApplication));
        mWakeLock = spy(createBackupWakeLock(mApplication));
        mBackupManager = spy(FakeIBackupManager.class);
        mBackupManager = spy(FakeIBackupManager.class);


        LocalServices.removeServiceForTest(UserManagerInternal.class);
        LocalServices.addService(UserManagerInternal.class, mUserManagerInternal);

        // Needed to be able to use a real BMS instead of a mock
        // Needed to be able to use a real BMS instead of a mock
        setUpBinderCallerAndApplicationAsSystem(mApplication);
        setUpBinderCallerAndApplicationAsSystem(mApplication);
        mBackupManagerService =
        mBackupManagerService =
Loading