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

Commit 458a4c10 authored by Jack Yu's avatar Jack Yu Committed by Automerger Merge Worker
Browse files

Merge changes from topic "get_all_subs" am: aa0bee6f am: b472bc5f

parents 4272b97e b472bc5f
Loading
Loading
Loading
Loading
+14 −4
Original line number Original line Diff line number Diff line
@@ -4542,18 +4542,28 @@ public class GsmCdmaPhone extends Phone {
            return;
            return;
        }
        }


        SubscriptionInfo info = SubscriptionController.getInstance().getSubInfoForIccId(
        SubscriptionInfo info;
        if (isSubscriptionManagerServiceEnabled()) {
            info = mSubscriptionManagerService
                    .getAllSubInfoList(mContext.getOpPackageName(), mContext.getAttributionTag())
                    .stream()
                    .filter(subInfo -> subInfo.getIccId().equals(IccUtils.stripTrailingFs(iccId)))
                    .findFirst()
                    .orElse(null);
        } else {
            info = SubscriptionController.getInstance().getSubInfoForIccId(
                    IccUtils.stripTrailingFs(iccId));
                    IccUtils.stripTrailingFs(iccId));
        }


        // If info is null, it could be a new subscription. By default we enable it.
        // If info is null, it could be a new subscription. By default we enable it.
        boolean expectedValue = info == null ? true : info.areUiccApplicationsEnabled();
        boolean expectedValue = info == null || info.areUiccApplicationsEnabled();


        // If for any reason current state is different from configured state, re-apply the
        // If for any reason current state is different from configured state, re-apply the
        // configured state.
        // configured state.
        if (expectedValue != mUiccApplicationsEnabled) {
        if (expectedValue != mUiccApplicationsEnabled) {
            mCi.enableUiccApplications(expectedValue, Message.obtain(
            mCi.enableUiccApplications(expectedValue, Message.obtain(
                    this, EVENT_REAPPLY_UICC_APPS_ENABLEMENT_DONE,
                    this, EVENT_REAPPLY_UICC_APPS_ENABLEMENT_DONE,
                    new Pair<Boolean, Integer>(expectedValue, retries)));
                    new Pair<>(expectedValue, retries)));
        }
        }
    }
    }


+178 −21
Original line number Original line Diff line number Diff line
@@ -31,6 +31,7 @@ import android.os.UserHandle;
import android.telephony.SubscriptionInfo;
import android.telephony.SubscriptionInfo;
import android.telephony.SubscriptionManager;
import android.telephony.SubscriptionManager;
import android.telephony.SubscriptionManager.OnSubscriptionsChangedListener;
import android.telephony.SubscriptionManager.OnSubscriptionsChangedListener;
import android.telephony.SubscriptionManager.PhoneNumberSource;
import android.telephony.SubscriptionManager.SubscriptionType;
import android.telephony.SubscriptionManager.SubscriptionType;
import android.telephony.TelephonyFrameworkInitializer;
import android.telephony.TelephonyFrameworkInitializer;
import android.telephony.TelephonyManager;
import android.telephony.TelephonyManager;
@@ -44,6 +45,7 @@ import com.android.internal.annotations.VisibleForTesting;
import com.android.internal.telephony.ISetOpportunisticDataCallback;
import com.android.internal.telephony.ISetOpportunisticDataCallback;
import com.android.internal.telephony.ISub;
import com.android.internal.telephony.ISub;
import com.android.internal.telephony.MultiSimSettingController;
import com.android.internal.telephony.MultiSimSettingController;
import com.android.internal.telephony.TelephonyPermissions;
import com.android.internal.telephony.subscription.SubscriptionDatabaseManager.SubscriptionDatabaseManagerCallback;
import com.android.internal.telephony.subscription.SubscriptionDatabaseManager.SubscriptionDatabaseManagerCallback;
import com.android.internal.telephony.uicc.IccUtils;
import com.android.internal.telephony.uicc.IccUtils;
import com.android.telephony.Rlog;
import com.android.telephony.Rlog;
@@ -51,11 +53,13 @@ import com.android.telephony.Rlog;
import java.io.FileDescriptor;
import java.io.FileDescriptor;
import java.io.PrintWriter;
import java.io.PrintWriter;
import java.util.Collections;
import java.util.Collections;
import java.util.Comparator;
import java.util.List;
import java.util.List;
import java.util.Map;
import java.util.Map;
import java.util.Set;
import java.util.Set;
import java.util.concurrent.ConcurrentHashMap;
import java.util.concurrent.ConcurrentHashMap;
import java.util.concurrent.Executor;
import java.util.concurrent.Executor;
import java.util.stream.Collectors;


/**
/**
 * The subscription manager service is the backend service of {@link SubscriptionManager}.
 * The subscription manager service is the backend service of {@link SubscriptionManager}.
@@ -75,6 +79,9 @@ public class SubscriptionManagerService extends ISub.Stub {
    @NonNull
    @NonNull
    private final Context mContext;
    private final Context mContext;


    /** Telephony manager instance. */
    private final TelephonyManager mTelephonyManager;

    /** The main handler of subscription manager service. */
    /** The main handler of subscription manager service. */
    @NonNull
    @NonNull
    private final Handler mHandler;
    private final Handler mHandler;
@@ -226,6 +233,7 @@ public class SubscriptionManagerService extends ISub.Stub {
    public SubscriptionManagerService(@NonNull Context context, @NonNull Looper looper) {
    public SubscriptionManagerService(@NonNull Context context, @NonNull Looper looper) {
        sInstance = this;
        sInstance = this;
        mContext = context;
        mContext = context;
        mTelephonyManager = context.getSystemService(TelephonyManager.class);
        mHandler = new Handler(looper);
        mHandler = new Handler(looper);
        TelephonyServiceManager.ServiceRegisterer subscriptionServiceRegisterer =
        TelephonyServiceManager.ServiceRegisterer subscriptionServiceRegisterer =
                TelephonyFrameworkInitializer
                TelephonyFrameworkInitializer
@@ -303,6 +311,98 @@ public class SubscriptionManagerService extends ISub.Stub {
        return sInstance;
        return sInstance;
    }
    }


    /**
     * Check whether the {@code callingPackage} has access to the phone number on the specified
     * {@code subId} or not.
     *
     * @param subId The subscription id.
     * @param callingPackage The package making the call.
     * @param callingFeatureId The feature in the package.
     * @param message Message to include in the exception or NoteOp.
     *
     * @return {@code true} if the caller has phone number access.
     */
    private boolean hasPhoneNumberAccess(int subId, @NonNull String callingPackage,
            @Nullable String callingFeatureId, @Nullable String message) {
        try {
            return TelephonyPermissions.checkCallingOrSelfReadPhoneNumber(mContext, subId,
                    callingPackage, callingFeatureId, message);
        } catch (SecurityException e) {
            return false;
        }
    }

    /**
     * Check whether the {@code callingPackage} has access to subscriber identifiers on the
     * specified {@code subId} or not.
     *
     * @param subId The subscription id.
     * @param callingPackage The package making the call.
     * @param callingFeatureId The feature in the package.
     * @param message Message to include in the exception or NoteOp.
     * @param reportFailure Indicates if failure should be reported.
     *
     * @return {@code true} if the caller has identifier access.
     */
    private boolean hasSubscriberIdentifierAccess(int subId, String callingPackage,
            String callingFeatureId, String message, boolean reportFailure) {
        try {
            return TelephonyPermissions.checkCallingOrSelfReadSubscriberIdentifiers(mContext, subId,
                    callingPackage, callingFeatureId, message, reportFailure);
        } catch (SecurityException e) {
            // A SecurityException indicates that the calling package is targeting at least the
            // minimum level that enforces identifier access restrictions and the new access
            // requirements are not met.
            return false;
        }
    }

    /**
     * Conditionally removes identifiers from the provided {@link SubscriptionInfo} if the {@code
     * callingPackage} does not meet the access requirements for identifiers and returns the
     * potentially modified object..
     *
     * <p>
     * If the caller does not have {@link Manifest.permission#READ_PHONE_NUMBERS} permission,
     * {@link SubscriptionInfo#getNumber()} will return empty string.
     * If the caller does not have {@link Manifest.permission#USE_ICC_AUTH_WITH_DEVICE_IDENTIFIER},
     * {@link SubscriptionInfo#getIccId()} and {@link SubscriptionInfo#getCardString()} will return
     * empty string, and {@link SubscriptionInfo#getGroupUuid()} will return {@code null}.
     *
     * @param subInfo The subscription info.
     * @param callingPackage The package making the call.
     * @param callingFeatureId The feature in the package.
     * @param message Message to include in the exception or NoteOp.
     *
     * @return The modified {@link SubscriptionInfo} depending on caller's permission.
     */
    @NonNull
    private SubscriptionInfo conditionallyRemoveIdentifiers(@NonNull SubscriptionInfo subInfo,
            @NonNull String callingPackage, @Nullable String callingFeatureId,
            @Nullable String message) {
        int subId = subInfo.getSubscriptionId();
        boolean hasIdentifierAccess = hasSubscriberIdentifierAccess(subId, callingPackage,
                callingFeatureId, message, true);
        boolean hasPhoneNumberAccess = hasPhoneNumberAccess(subId, callingPackage,
                callingFeatureId, message);

        if (hasIdentifierAccess && hasPhoneNumberAccess) {
            return subInfo;
        }

        SubscriptionInfo.Builder result = new SubscriptionInfo.Builder(subInfo);
        if (!hasIdentifierAccess) {
            result.setIccId(null);
            result.setCardString(null);
            result.setGroupUuid(null);
        }

        if (!hasPhoneNumberAccess) {
            result.setNumber(null);
        }
        return result.build();
    }

    /**
    /**
     * Set the subscription carrier id.
     * Set the subscription carrier id.
     *
     *
@@ -337,30 +437,70 @@ public class SubscriptionManagerService extends ISub.Stub {
    }
    }


    /**
    /**
     * Get all subscription info records from SIMs that are inserted now or were inserted before.
     *
     * <p>
     * If the caller does not have {@link Manifest.permission#READ_PHONE_NUMBERS} permission,
     * {@link SubscriptionInfo#getNumber()} will return empty string.
     * If the caller does not have {@link Manifest.permission#USE_ICC_AUTH_WITH_DEVICE_IDENTIFIER},
     * {@link SubscriptionInfo#getIccId()} and {@link SubscriptionInfo#getCardString()} will return
     * empty string, and {@link SubscriptionInfo#getGroupUuid()} will return {@code null}.
     *
     * <p>
     * The carrier app will always have full {@link SubscriptionInfo} for the subscriptions
     * that it has carrier privilege.
     *
     * @return List of all {@link SubscriptionInfo} records from SIMs that are inserted or
     * inserted before. Sorted by {@link SubscriptionInfo#getSimSlotIndex()}, then
     * {@link SubscriptionInfo#getSubscriptionId()}.
     *
     * @param callingPackage The package making the call.
     * @param callingPackage The package making the call.
     * @param callingFeatureId The feature in the package
     * @param callingFeatureId The feature in the package.
     * @return a list of all subscriptions in the database, this includes
     *
     * all subscriptions that have been seen.
     */
     */
    @Override
    @Override
    public List<SubscriptionInfo> getAllSubInfoList(@NonNull String callingPackage,
    public List<SubscriptionInfo> getAllSubInfoList(@NonNull String callingPackage,
            @NonNull String callingFeatureId) {
            @Nullable String callingFeatureId) {
        return null;
        // Check if the caller has READ_PHONE_STATE, READ_PRIVILEGED_PHONE_STATE, or carrier
        // privilege on any active subscription. The carrier app will get full subscription infos
        // on the subs it has carrier privilege.
        if (!TelephonyPermissions.checkReadPhoneStateOnAnyActiveSub(mContext,
                Binder.getCallingPid(), Binder.getCallingUid(), callingPackage, callingFeatureId,
                "getAllSubInfoList")) {
            throw new SecurityException("Need READ_PHONE_STATE, READ_PRIVILEGED_PHONE_STATE, or "
                    + "carrier privilege to call getAllSubInfoList");
        }

        final long identity = Binder.clearCallingIdentity();
        try {
            return mSubscriptionDatabaseManager.getAllSubscriptions().stream()
                    // Remove the identifier if the caller does not have sufficient permission.
                    // carrier apps will get full subscription info on the subscriptions associated
                    // to them.
                    .map(subInfo -> conditionallyRemoveIdentifiers(subInfo.toSubscriptionInfo(),
                            callingPackage, callingFeatureId, "getAllSubInfoList"))
                    .sorted(Comparator.comparing(SubscriptionInfo::getSimSlotIndex)
                            .thenComparing(SubscriptionInfo::getSubscriptionId))
                    .collect(Collectors.toList());

        } finally {
            Binder.restoreCallingIdentity(identity);
        }
    }
    }


    /**
    /**
     * Get the active {@link SubscriptionInfo} with the subscription id key.
     * Get the active {@link SubscriptionInfo} with the subscription id key.
     *
     *
     * @param subId The unique {@link SubscriptionInfo} key in database
     * @param subId The unique {@link SubscriptionInfo} key in database
     * @param callingPackage The package making the call
     * @param callingPackage The package making the call.
     * @param callingFeatureId The feature in the package
     * @param callingFeatureId The feature in the package.
     *
     *
     * @return The subscription info.
     * @return The subscription info.
     */
     */
    @Override
    @Override
    @Nullable
    @Nullable
    public SubscriptionInfo getActiveSubscriptionInfo(int subId, @NonNull String callingPackage,
    public SubscriptionInfo getActiveSubscriptionInfo(int subId, @NonNull String callingPackage,
            @NonNull String callingFeatureId) {
            @Nullable String callingFeatureId) {
        return null;
        return null;
    }
    }


@@ -376,7 +516,7 @@ public class SubscriptionManagerService extends ISub.Stub {
    @Override
    @Override
    @Nullable
    @Nullable
    public SubscriptionInfo getActiveSubscriptionInfoForIccId(@NonNull String iccId,
    public SubscriptionInfo getActiveSubscriptionInfoForIccId(@NonNull String iccId,
            @NonNull String callingPackage, @NonNull String callingFeatureId) {
            @NonNull String callingPackage, @Nullable String callingFeatureId) {
        return null;
        return null;
    }
    }


@@ -391,7 +531,7 @@ public class SubscriptionManagerService extends ISub.Stub {
     */
     */
    @Override
    @Override
    public SubscriptionInfo getActiveSubscriptionInfoForSimSlotIndex(int slotIndex,
    public SubscriptionInfo getActiveSubscriptionInfoForSimSlotIndex(int slotIndex,
            @NonNull String callingPackage, @NonNull String callingFeatureId) {
            @NonNull String callingPackage, @Nullable String callingFeatureId) {
        return null;
        return null;
    }
    }


@@ -421,7 +561,7 @@ public class SubscriptionManagerService extends ISub.Stub {
     */
     */
    @Override
    @Override
    public List<SubscriptionInfo> getActiveSubscriptionInfoList(@NonNull String callingPackage,
    public List<SubscriptionInfo> getActiveSubscriptionInfoList(@NonNull String callingPackage,
            @NonNull String callingFeatureId) {
            @Nullable String callingFeatureId) {
        return null;
        return null;
    }
    }


@@ -434,7 +574,7 @@ public class SubscriptionManagerService extends ISub.Stub {
     */
     */
    @Override
    @Override
    public int getActiveSubInfoCount(@NonNull String callingPackage,
    public int getActiveSubInfoCount(@NonNull String callingPackage,
            @NonNull String callingFeatureId) {
            @Nullable String callingFeatureId) {
        return 0;
        return 0;
    }
    }


@@ -451,7 +591,7 @@ public class SubscriptionManagerService extends ISub.Stub {
     */
     */
    @Override
    @Override
    public List<SubscriptionInfo> getAvailableSubscriptionInfoList(@NonNull String callingPackage,
    public List<SubscriptionInfo> getAvailableSubscriptionInfoList(@NonNull String callingPackage,
            @NonNull String callingFeatureId) {
            @Nullable String callingFeatureId) {
        return null;
        return null;
    }
    }


@@ -655,7 +795,7 @@ public class SubscriptionManagerService extends ISub.Stub {
    @Override
    @Override
    @NonNull
    @NonNull
    public List<SubscriptionInfo> getOpportunisticSubscriptions(@NonNull String callingPackage,
    public List<SubscriptionInfo> getOpportunisticSubscriptions(@NonNull String callingPackage,
            @NonNull String callingFeatureId) {
            @Nullable String callingFeatureId) {
        return Collections.emptyList();
        return Collections.emptyList();
    }
    }


@@ -671,7 +811,7 @@ public class SubscriptionManagerService extends ISub.Stub {


    @Override
    @Override
    public List<SubscriptionInfo> getSubscriptionsInGroup(@NonNull ParcelUuid groupUuid,
    public List<SubscriptionInfo> getSubscriptionsInGroup(@NonNull ParcelUuid groupUuid,
            @NonNull String callingPackage, @NonNull String callingFeatureId) {
            @NonNull String callingPackage, @Nullable String callingFeatureId) {
        return null;
        return null;
    }
    }


@@ -761,7 +901,7 @@ public class SubscriptionManagerService extends ISub.Stub {


    @Override
    @Override
    public String getSubscriptionProperty(int subId, @NonNull String propKey,
    public String getSubscriptionProperty(int subId, @NonNull String propKey,
            @NonNull String callingPackage, @NonNull String callingFeatureId) {
            @NonNull String callingPackage, @Nullable String callingFeatureId) {
        return null;
        return null;
    }
    }


@@ -787,7 +927,7 @@ public class SubscriptionManagerService extends ISub.Stub {


    @Override
    @Override
    public boolean isActiveSubId(int subId, @NonNull String callingPackage,
    public boolean isActiveSubId(int subId, @NonNull String callingPackage,
            @NonNull String callingFeatureId) {
            @Nullable String callingFeatureId) {
        return true;
        return true;
    }
    }


@@ -819,19 +959,36 @@ public class SubscriptionManagerService extends ISub.Stub {


    @Override
    @Override
    public String getPhoneNumber(int subId, int source,
    public String getPhoneNumber(int subId, int source,
            @NonNull String callingPackage, @NonNull String callingFeatureId) {
            @NonNull String callingPackage, @Nullable String callingFeatureId) {
        return null;
        return null;
    }
    }


    @Override
    @Override
    public String getPhoneNumberFromFirstAvailableSource(int subId,
    public String getPhoneNumberFromFirstAvailableSource(int subId,
            @NonNull String callingPackage, @NonNull String callingFeatureId) {
            @NonNull String callingPackage, @Nullable String callingFeatureId) {
        return null;
        return null;
    }
    }


    @Override
    @Override
    public void setPhoneNumber(int subId, int source, @NonNull String number,
    public void setPhoneNumber(int subId, @PhoneNumberSource int source, @NonNull String number,
            @NonNull String callingPackage, @NonNull String callingFeatureId) {
            @NonNull String callingPackage, @Nullable String callingFeatureId) {
        if (source != SubscriptionManager.PHONE_NUMBER_SOURCE_CARRIER) {
            throw new IllegalArgumentException("setPhoneNumber doesn't accept source "
                    + SubscriptionManager.phoneNumberSourceToString(source));
        }
        if (!TelephonyPermissions.checkCarrierPrivilegeForSubId(mContext, subId)) {
            throw new SecurityException("setPhoneNumber for CARRIER needs carrier privilege.");
        }
        if (number == null) {
            throw new NullPointerException("invalid number null");
        }

        final long identity = Binder.clearCallingIdentity();
        try {
            mSubscriptionDatabaseManager.setNumberFromCarrier(subId, number);
        } finally {
            Binder.restoreCallingIdentity(identity);
        }
    }
    }


    /**
    /**
+143 −1
Original line number Original line Diff line number Diff line
@@ -16,29 +16,44 @@


package com.android.internal.telephony.subscription;
package com.android.internal.telephony.subscription;


import static android.Manifest.permission.READ_PHONE_STATE;

import static com.android.internal.telephony.TelephonyTestUtils.waitForMs;
import static com.android.internal.telephony.TelephonyTestUtils.waitForMs;
import static com.android.internal.telephony.subscription.SubscriptionDatabaseManagerTest.FAKE_CARRIER_ID2;
import static com.android.internal.telephony.subscription.SubscriptionDatabaseManagerTest.FAKE_CARRIER_ID2;
import static com.android.internal.telephony.subscription.SubscriptionDatabaseManagerTest.FAKE_CARRIER_NAME1;
import static com.android.internal.telephony.subscription.SubscriptionDatabaseManagerTest.FAKE_CARRIER_NAME1;
import static com.android.internal.telephony.subscription.SubscriptionDatabaseManagerTest.FAKE_CARRIER_NAME2;
import static com.android.internal.telephony.subscription.SubscriptionDatabaseManagerTest.FAKE_COUNTRY_CODE2;
import static com.android.internal.telephony.subscription.SubscriptionDatabaseManagerTest.FAKE_COUNTRY_CODE2;
import static com.android.internal.telephony.subscription.SubscriptionDatabaseManagerTest.FAKE_ICCID1;
import static com.android.internal.telephony.subscription.SubscriptionDatabaseManagerTest.FAKE_ICCID1;
import static com.android.internal.telephony.subscription.SubscriptionDatabaseManagerTest.FAKE_ICCID2;
import static com.android.internal.telephony.subscription.SubscriptionDatabaseManagerTest.FAKE_MCC2;
import static com.android.internal.telephony.subscription.SubscriptionDatabaseManagerTest.FAKE_MCC2;
import static com.android.internal.telephony.subscription.SubscriptionDatabaseManagerTest.FAKE_MNC2;
import static com.android.internal.telephony.subscription.SubscriptionDatabaseManagerTest.FAKE_MNC2;
import static com.android.internal.telephony.subscription.SubscriptionDatabaseManagerTest.FAKE_PHONE_NUMBER2;


import static com.google.common.truth.Truth.assertThat;
import static com.google.common.truth.Truth.assertThat;


import static org.junit.Assert.assertThrows;
import static org.mockito.ArgumentMatchers.any;
import static org.mockito.ArgumentMatchers.any;
import static org.mockito.ArgumentMatchers.anyInt;
import static org.mockito.ArgumentMatchers.anyString;
import static org.mockito.ArgumentMatchers.eq;
import static org.mockito.ArgumentMatchers.eq;
import static org.mockito.ArgumentMatchers.nullable;
import static org.mockito.Mockito.doAnswer;
import static org.mockito.Mockito.doAnswer;
import static org.mockito.Mockito.doReturn;
import static org.mockito.Mockito.times;
import static org.mockito.Mockito.times;
import static org.mockito.Mockito.verify;
import static org.mockito.Mockito.verify;


import android.app.AppOpsManager;
import android.content.pm.PackageManager;
import android.os.Build;
import android.os.Looper;
import android.os.Looper;
import android.provider.Telephony;
import android.provider.Telephony;
import android.telephony.SubscriptionInfo;
import android.telephony.SubscriptionManager;
import android.telephony.SubscriptionManager;
import android.test.mock.MockContentResolver;
import android.test.mock.MockContentResolver;
import android.testing.AndroidTestingRunner;
import android.testing.AndroidTestingRunner;
import android.testing.TestableLooper;
import android.testing.TestableLooper;


import com.android.internal.telephony.ContextFixture;
import com.android.internal.telephony.TelephonyTest;
import com.android.internal.telephony.TelephonyTest;
import com.android.internal.telephony.subscription.SubscriptionDatabaseManagerTest.SubscriptionProvider;
import com.android.internal.telephony.subscription.SubscriptionDatabaseManagerTest.SubscriptionProvider;
import com.android.internal.telephony.subscription.SubscriptionManagerService.SubscriptionManagerServiceCallback;
import com.android.internal.telephony.subscription.SubscriptionManagerService.SubscriptionManagerServiceCallback;
@@ -49,10 +64,16 @@ import org.junit.Test;
import org.junit.runner.RunWith;
import org.junit.runner.RunWith;
import org.mockito.Mockito;
import org.mockito.Mockito;


import java.util.List;

@RunWith(AndroidTestingRunner.class)
@RunWith(AndroidTestingRunner.class)
@TestableLooper.RunWithLooper
@TestableLooper.RunWithLooper
public class SubscriptionManagerServiceTest extends TelephonyTest {
public class SubscriptionManagerServiceTest extends TelephonyTest {


    private static final String CALLING_PACKAGE = "calling_package";

    private static final String CALLING_FEATURE = "calling_feature";

    private SubscriptionManagerService mSubscriptionManagerServiceUT;
    private SubscriptionManagerService mSubscriptionManagerServiceUT;


    private final SubscriptionProvider mSubscriptionProvider = new SubscriptionProvider();
    private final SubscriptionProvider mSubscriptionProvider = new SubscriptionProvider();
@@ -64,7 +85,7 @@ public class SubscriptionManagerServiceTest extends TelephonyTest {
    public void setUp() throws Exception {
    public void setUp() throws Exception {
        logd("SubscriptionManagerServiceTest +Setup!");
        logd("SubscriptionManagerServiceTest +Setup!");
        super.setUp(getClass().getSimpleName());
        super.setUp(getClass().getSimpleName());

        setupMocksForTelephonyPermissions(Build.VERSION_CODES.UPSIDE_DOWN_CAKE);
        mMockedSubscriptionManagerServiceCallback = Mockito.mock(
        mMockedSubscriptionManagerServiceCallback = Mockito.mock(
                SubscriptionManagerServiceCallback.class);
                SubscriptionManagerServiceCallback.class);
        ((MockContentResolver) mContext.getContentResolver()).addProvider(
        ((MockContentResolver) mContext.getContentResolver()).addProvider(
@@ -160,4 +181,125 @@ public class SubscriptionManagerServiceTest extends TelephonyTest {
        assertThat(subInfo.getCarrierId()).isEqualTo(FAKE_CARRIER_ID2);
        assertThat(subInfo.getCarrierId()).isEqualTo(FAKE_CARRIER_ID2);
        verify(mMockedSubscriptionManagerServiceCallback).onSubscriptionChanged(eq(1));
        verify(mMockedSubscriptionManagerServiceCallback).onSubscriptionChanged(eq(1));
    }
    }

    @Test
    public void testSetPhoneNumber() {
        mSubscriptionManagerServiceUT.addSubInfo(FAKE_ICCID1, FAKE_CARRIER_NAME1,
                0, SubscriptionManager.SUBSCRIPTION_TYPE_LOCAL_SIM);
        processAllMessages();

        verify(mMockedSubscriptionManagerServiceCallback).onSubscriptionChanged(eq(1));
        Mockito.clearInvocations(mMockedSubscriptionManagerServiceCallback);

        // Source IMS is not acceptable
        assertThrows(IllegalArgumentException.class,
                () -> mSubscriptionManagerServiceUT.setPhoneNumber(1,
                        SubscriptionManager.PHONE_NUMBER_SOURCE_IMS, FAKE_PHONE_NUMBER2,
                        CALLING_PACKAGE, CALLING_FEATURE));

        // Caller does not have carrier privilege
        assertThrows(SecurityException.class,
                () -> mSubscriptionManagerServiceUT.setPhoneNumber(1,
                        SubscriptionManager.PHONE_NUMBER_SOURCE_CARRIER, FAKE_PHONE_NUMBER2,
                        CALLING_PACKAGE, CALLING_FEATURE));

        // Grant carrier privilege
        setCarrierPrivilegesForSubId(true, 1);

        mSubscriptionManagerServiceUT.setPhoneNumber(1,
                SubscriptionManager.PHONE_NUMBER_SOURCE_CARRIER, FAKE_PHONE_NUMBER2,
                CALLING_PACKAGE, CALLING_FEATURE);
        processAllMessages();

        SubscriptionInfoInternal subInfo = mSubscriptionManagerServiceUT
                .getSubscriptionInfoInternal(1);
        assertThat(subInfo).isNotNull();
        assertThat(subInfo.getNumberFromCarrier()).isEqualTo(FAKE_PHONE_NUMBER2);
        verify(mMockedSubscriptionManagerServiceCallback).onSubscriptionChanged(eq(1));
    }

    @Test
    public void testGetAllSubInfoList() {
        doReturn(new int[]{1, 2}).when(mSubscriptionManager).getCompleteActiveSubscriptionIdList();
        mSubscriptionManagerServiceUT.addSubInfo(FAKE_ICCID1, FAKE_CARRIER_NAME1,
                0, SubscriptionManager.SUBSCRIPTION_TYPE_LOCAL_SIM);
        mSubscriptionManagerServiceUT.addSubInfo(FAKE_ICCID2, FAKE_CARRIER_NAME2,
                1, SubscriptionManager.SUBSCRIPTION_TYPE_LOCAL_SIM);
        processAllMessages();

        verify(mMockedSubscriptionManagerServiceCallback).onSubscriptionChanged(eq(2));

        // Revoke all permissions.
        mContextFixture.removeCallingOrSelfPermission(ContextFixture.PERMISSION_ENABLE_ALL);
        doReturn(AppOpsManager.MODE_DEFAULT).when(mAppOpsManager).noteOpNoThrow(anyString(),
                anyInt(), nullable(String.class), nullable(String.class), nullable(String.class));
        setIdentifierAccess(false);
        setPhoneNumberAccess(PackageManager.PERMISSION_DENIED);

        // Should throw security exception if the caller does not have permission.
        assertThrows(SecurityException.class,
                () -> mSubscriptionManagerServiceUT.getAllSubInfoList("", null));

        // Grant carrier privilege for sub 1
        setCarrierPrivilegesForSubId(true, 1);
        // Grant carrier privilege for sub 2
        setCarrierPrivilegesForSubId(true, 2);

        List<SubscriptionInfo> subInfos = mSubscriptionManagerServiceUT.getAllSubInfoList("", null);
        assertThat(subInfos).hasSize(2);

        assertThat(subInfos.get(0).getIccId()).isEqualTo(FAKE_ICCID1);
        assertThat(subInfos.get(0).getDisplayName()).isEqualTo(FAKE_CARRIER_NAME1);
        assertThat(subInfos.get(0).getSubscriptionType()).isEqualTo(
                SubscriptionManager.SUBSCRIPTION_TYPE_LOCAL_SIM);
        assertThat(subInfos.get(0).getSimSlotIndex()).isEqualTo(0);

        assertThat(subInfos.get(1).getIccId()).isEqualTo(FAKE_ICCID2);
        assertThat(subInfos.get(1).getDisplayName()).isEqualTo(FAKE_CARRIER_NAME2);
        assertThat(subInfos.get(1).getSubscriptionType()).isEqualTo(
                SubscriptionManager.SUBSCRIPTION_TYPE_LOCAL_SIM);
        assertThat(subInfos.get(1).getSimSlotIndex()).isEqualTo(1);

        // Revoke carrier privilege for sub 2
        setCarrierPrivilegesForSubId(false, 2);

        subInfos = mSubscriptionManagerServiceUT.getAllSubInfoList("", null);
        assertThat(subInfos).hasSize(2);

        assertThat(subInfos.get(0).getIccId()).isEqualTo(FAKE_ICCID1);
        assertThat(subInfos.get(0).getDisplayName()).isEqualTo(FAKE_CARRIER_NAME1);
        assertThat(subInfos.get(0).getSubscriptionType()).isEqualTo(
                SubscriptionManager.SUBSCRIPTION_TYPE_LOCAL_SIM);
        assertThat(subInfos.get(0).getSimSlotIndex()).isEqualTo(0);

        // ICCID should be empty due to insufficient permission.
        assertThat(subInfos.get(1).getIccId()).isEmpty();
        assertThat(subInfos.get(1).getDisplayName()).isEqualTo(FAKE_CARRIER_NAME2);
        assertThat(subInfos.get(1).getSubscriptionType()).isEqualTo(
                SubscriptionManager.SUBSCRIPTION_TYPE_LOCAL_SIM);
        assertThat(subInfos.get(1).getSimSlotIndex()).isEqualTo(1);

        // Grant READ_PHONE_STATE permission
        mContextFixture.addCallingOrSelfPermission(READ_PHONE_STATE);
        // Grant identifier access
        setIdentifierAccess(true);
        // Revoke carrier privileges.
        setCarrierPrivilegesForSubId(false, 1);
        setCarrierPrivilegesForSubId(false, 2);

        subInfos = mSubscriptionManagerServiceUT.getAllSubInfoList("", null);
        assertThat(subInfos).hasSize(2);

        assertThat(subInfos.get(0).getIccId()).isEqualTo(FAKE_ICCID1);
        assertThat(subInfos.get(0).getDisplayName()).isEqualTo(FAKE_CARRIER_NAME1);
        assertThat(subInfos.get(0).getSubscriptionType()).isEqualTo(
                SubscriptionManager.SUBSCRIPTION_TYPE_LOCAL_SIM);
        assertThat(subInfos.get(0).getSimSlotIndex()).isEqualTo(0);

        assertThat(subInfos.get(1).getIccId()).isEqualTo(FAKE_ICCID2);
        assertThat(subInfos.get(1).getDisplayName()).isEqualTo(FAKE_CARRIER_NAME2);
        assertThat(subInfos.get(1).getSubscriptionType()).isEqualTo(
                SubscriptionManager.SUBSCRIPTION_TYPE_LOCAL_SIM);
        assertThat(subInfos.get(1).getSimSlotIndex()).isEqualTo(1);
    }
}
}