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

Commit d6c19f96 authored by Jason Parks's avatar Jason Parks Committed by Automerger Merge Worker
Browse files

Fix issue with upgrading from previous user versions. am: f0d456b0

parents 8df20099 f0d456b0
Loading
Loading
Loading
Loading
+17 −6
Original line number Diff line number Diff line
@@ -3705,7 +3705,8 @@ public class UserManagerService extends IUserManager.Stub {
                    if (type == XmlPullParser.START_TAG) {
                        final String name = parser.getName();
                        if (name.equals(TAG_USER)) {
                            UserData userData = readUserLP(parser.getAttributeInt(null, ATTR_ID));
                            UserData userData = readUserLP(parser.getAttributeInt(null, ATTR_ID),
                                    mUserVersion);

                            if (userData != null) {
                                synchronized (mUsersLock) {
@@ -4386,7 +4387,7 @@ public class UserManagerService extends IUserManager.Stub {
    }

    @GuardedBy({"mPackagesLock"})
    private UserData readUserLP(int id) {
    private UserData readUserLP(int id, int userVersion) {
        try (ResilientAtomicFile file = getUserFile(id)) {
            FileInputStream fis = null;
            try {
@@ -4395,19 +4396,19 @@ public class UserManagerService extends IUserManager.Stub {
                    Slog.e(LOG_TAG, "User info not found, returning null, user id: " + id);
                    return null;
                }
                return readUserLP(id, fis);
                return readUserLP(id, fis, userVersion);
            } catch (Exception e) {
                // Remove corrupted file and retry.
                Slog.e(LOG_TAG, "Error reading user info, user id: " + id);
                file.failRead(fis, e);
                return readUserLP(id);
                return readUserLP(id, userVersion);
            }
        }
    }

    @GuardedBy({"mPackagesLock"})
    @VisibleForTesting
    UserData readUserLP(int id, InputStream is) throws IOException,
    UserData readUserLP(int id, InputStream is, int userVersion) throws IOException,
            XmlPullParserException {
        int flags = 0;
        String userType = null;
@@ -4500,7 +4501,17 @@ public class UserManagerService extends IUserManager.Stub {
                } else if (TAG_DEVICE_POLICY_RESTRICTIONS.equals(tag)) {
                    legacyLocalRestrictions = UserRestrictionsUtils.readRestrictions(parser);
                } else if (TAG_DEVICE_POLICY_LOCAL_RESTRICTIONS.equals(tag)) {
                    if (userVersion < 10) {
                        // Prior to version 10, the local user restrictions were stored as sub tags
                        // grouped by the user id of the source user. The source is no longer stored
                        // on versions 10+ as this is now stored in the DevicePolicyEngine.
                        RestrictionsSet oldLocalRestrictions =
                                RestrictionsSet.readRestrictions(
                                    parser, TAG_DEVICE_POLICY_LOCAL_RESTRICTIONS);
                        localRestrictions = oldLocalRestrictions.mergeAll();
                    } else {
                        localRestrictions = UserRestrictionsUtils.readRestrictions(parser);
                    }
                } else if (TAG_DEVICE_POLICY_GLOBAL_RESTRICTIONS.equals(tag)) {
                    globalRestrictions = UserRestrictionsUtils.readRestrictions(parser);
                } else if (TAG_ACCOUNT.equals(tag)) {
+20 −0
Original line number Diff line number Diff line
<user id="100"
    serialNumber="0"
    flags="3091"
    type="android.os.usertype.full.SYSTEM"
    created="0"
    lastLoggedIn="0"
    lastLoggedInFingerprint="0"
    profileBadge="0">
  <restrictions no_oem_unlock="true" />
  <device_policy_local_restrictions>
    <restrictions_user user_id="0">
      <restrictions no_camera="true" />
    </restrictions_user>
    <restrictions_user user_id="100">
      <restrictions no_camera="true" />
      <restrictions no_install_unknown_sources="true" />
    </restrictions_user>
  </device_policy_local_restrictions>
  <ignorePrepareStorageErrors>false</ignorePrepareStorageErrors>
</user>
 No newline at end of file
+54 −2
Original line number Diff line number Diff line
@@ -43,27 +43,33 @@ import android.annotation.UserIdInt;
import android.app.PropertyInvalidatedCache;
import android.content.pm.UserInfo;
import android.content.pm.UserInfo.UserInfoFlag;
import android.content.res.Resources;
import android.os.Looper;
import android.os.Parcel;
import android.os.UserHandle;
import android.os.UserManager;
import android.platform.test.annotations.Presubmit;
import android.text.TextUtils;
import android.util.Xml;

import androidx.test.InstrumentationRegistry;
import androidx.test.filters.MediumTest;
import androidx.test.runner.AndroidJUnit4;

import com.android.frameworks.servicestests.R;
import com.android.server.LocalServices;
import com.android.server.pm.UserManagerService.UserData;

import org.junit.Before;
import org.junit.Test;
import org.junit.runner.RunWith;
import org.xmlpull.v1.XmlPullParser;
import org.xmlpull.v1.XmlSerializer;

import java.io.ByteArrayInputStream;
import java.io.ByteArrayOutputStream;
import java.io.DataOutputStream;
import java.nio.charset.StandardCharsets;
import java.util.List;

/**
@@ -76,6 +82,7 @@ import java.util.List;
@MediumTest
public class UserManagerServiceUserInfoTest {
    private UserManagerService mUserManagerService;
    private Resources mResources;

    @Before
    public void setup() {
@@ -95,6 +102,8 @@ public class UserManagerServiceUserInfoTest {
        assertEquals("Multiple users so this test can't run.", 1, users.size());
        assertEquals("Only user present isn't the system user.",
                UserHandle.USER_SYSTEM, users.get(0).id);

        mResources = InstrumentationRegistry.getTargetContext().getResources();
    }

    @Test
@@ -108,7 +117,7 @@ public class UserManagerServiceUserInfoTest {
        byte[] bytes = baos.toByteArray();

        UserData read = mUserManagerService.readUserLP(
                data.info.id, new ByteArrayInputStream(bytes));
                data.info.id, new ByteArrayInputStream(bytes), 0);

        assertUserInfoEquals(data.info, read.info, /* parcelCopy= */ false);
    }
@@ -135,7 +144,11 @@ public class UserManagerServiceUserInfoTest {
        // Clear the restrictions to see if they are properly read in from the user file.
        setUserRestrictions(data.info.id, globalRestriction, localRestriction, false);

        mUserManagerService.readUserLP(data.info.id, new ByteArrayInputStream(bytes));
        final int userVersion = 10;
        //read the secondary and SYSTEM user file to fetch local/global device policy restrictions.
        mUserManagerService.readUserLP(data.info.id, new ByteArrayInputStream(bytes),
                userVersion);

        assertTrue(mUserManagerService.hasUserRestrictionOnAnyUser(globalRestriction));
        assertTrue(mUserManagerService.hasUserRestrictionOnAnyUser(localRestriction));
    }
@@ -286,6 +299,45 @@ public class UserManagerServiceUserInfoTest {
        assertTrue(mUserManagerService.isUserOfType(106, USER_TYPE_FULL_DEMO));
    }

    /** Tests readUserLP upgrading from version 9 to 10+. */
    @Test
    public void testUserRestrictionsUpgradeFromV9() throws Exception {
        final String[] localRestrictions = new String[] {
            UserManager.DISALLOW_CAMERA,
            UserManager.DISALLOW_INSTALL_UNKNOWN_SOURCES,
        };

        final int userId = 100;
        UserData data = new UserData();
        data.info = createUser(userId, FLAG_FULL, "A type");

        mUserManagerService.putUserInfo(data.info);

        for (String restriction : localRestrictions) {
            assertFalse(mUserManagerService.hasBaseUserRestriction(restriction, userId));
            assertFalse(mUserManagerService.hasUserRestriction(restriction, userId));
        }

        // Convert the xml resource to the system storage xml format.
        ByteArrayOutputStream baos = new ByteArrayOutputStream();
        DataOutputStream os = new DataOutputStream(baos);
        XmlPullParser in = mResources.getXml(R.xml.user_100_v9);
        XmlSerializer out = Xml.newBinarySerializer();
        out.setOutput(os, StandardCharsets.UTF_8.name());
        Xml.copy(in, out);
        byte[] userBytes = baos.toByteArray();
        baos.reset();

        final int userVersion = 9;
        mUserManagerService.readUserLP(data.info.id, new ByteArrayInputStream(userBytes),
                userVersion);

        for (String restriction : localRestrictions) {
            assertFalse(mUserManagerService.hasBaseUserRestriction(restriction, userId));
            assertTrue(mUserManagerService.hasUserRestriction(restriction, userId));
        }
    }

    /** Creates a UserInfo with the given flags and userType. */
    private UserInfo createUser(@UserIdInt int userId, @UserInfoFlag int flags, String userType) {
        return new UserInfo(userId, "A Name", "A path", flags, userType);