• Home
  • Line#
  • Scopes#
  • Navigate#
  • Raw
  • Download
1 /*
2  * Copyright (C) 2015 The Android Open Source Project
3  *
4  * Licensed under the Apache License, Version 2.0 (the "License");
5  * you may not use this file except in compliance with the License.
6  * You may obtain a copy of the License at
7  *
8  *      http://www.apache.org/licenses/LICENSE-2.0
9  *
10  * Unless required by applicable law or agreed to in writing, software
11  * distributed under the License is distributed on an "AS IS" BASIS,
12  * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
13  * See the License for the specific language governing permissions and
14  * limitations under the License.
15  */
16 
17 package android.telephony.cts;
18 
19 import static android.net.NetworkCapabilities.NET_CAPABILITY_INTERNET;
20 import static android.net.NetworkCapabilities.NET_CAPABILITY_NOT_CONGESTED;
21 import static android.net.NetworkCapabilities.NET_CAPABILITY_NOT_RESTRICTED;
22 import static android.net.NetworkCapabilities.NET_CAPABILITY_TEMPORARILY_NOT_METERED;
23 import static android.net.NetworkCapabilities.TRANSPORT_CELLULAR;
24 import static android.telephony.TelephonyManager.SET_OPPORTUNISTIC_SUB_SUCCESS;
25 
26 import static com.google.common.truth.Truth.assertThat;
27 
28 import static org.junit.Assert.assertEquals;
29 import static org.junit.Assert.assertFalse;
30 import static org.junit.Assert.assertNotEquals;
31 import static org.junit.Assert.assertNotNull;
32 import static org.junit.Assert.assertNull;
33 import static org.junit.Assert.assertTrue;
34 import static org.junit.Assert.fail;
35 import static org.junit.Assume.assumeTrue;
36 
37 import android.annotation.Nullable;
38 import android.app.AppOpsManager;
39 import android.app.UiAutomation;
40 import android.content.BroadcastReceiver;
41 import android.content.Context;
42 import android.content.Intent;
43 import android.content.IntentFilter;
44 import android.content.pm.PackageManager;
45 import android.content.res.Resources;
46 import android.net.ConnectivityManager;
47 import android.net.ConnectivityManager.NetworkCallback;
48 import android.net.Network;
49 import android.net.NetworkCapabilities;
50 import android.net.NetworkRequest;
51 import android.net.Uri;
52 import android.os.Looper;
53 import android.os.ParcelUuid;
54 import android.os.PersistableBundle;
55 import android.os.Process;
56 import android.telephony.CarrierConfigManager;
57 import android.telephony.SubscriptionInfo;
58 import android.telephony.SubscriptionManager;
59 import android.telephony.SubscriptionPlan;
60 import android.telephony.TelephonyManager;
61 import android.telephony.cts.util.TelephonyUtils;
62 import android.telephony.ims.ImsException;
63 import android.telephony.ims.ImsManager;
64 import android.telephony.ims.ImsMmTelManager;
65 import android.telephony.ims.ImsRcsManager;
66 import android.telephony.ims.RcsUceAdapter;
67 
68 import androidx.test.InstrumentationRegistry;
69 
70 import com.android.compatibility.common.util.ApiTest;
71 import com.android.compatibility.common.util.CarrierPrivilegeUtils;
72 import com.android.compatibility.common.util.PropertyUtil;
73 import com.android.compatibility.common.util.ShellIdentityUtils;
74 import com.android.compatibility.common.util.SystemUtil;
75 import com.android.compatibility.common.util.TestThread;
76 import com.android.internal.util.ArrayUtils;
77 
78 import org.junit.After;
79 import org.junit.AfterClass;
80 import org.junit.Before;
81 import org.junit.BeforeClass;
82 import org.junit.Test;
83 
84 import java.io.ByteArrayInputStream;
85 import java.io.IOException;
86 import java.time.Period;
87 import java.time.ZonedDateTime;
88 import java.util.ArrayList;
89 import java.util.Arrays;
90 import java.util.HashSet;
91 import java.util.List;
92 import java.util.Set;
93 import java.util.UUID;
94 import java.util.concurrent.CountDownLatch;
95 import java.util.concurrent.Executor;
96 import java.util.concurrent.LinkedBlockingQueue;
97 import java.util.concurrent.TimeUnit;
98 import java.util.concurrent.atomic.AtomicBoolean;
99 import java.util.function.BooleanSupplier;
100 import java.util.function.Consumer;
101 import java.util.function.Predicate;
102 import java.util.stream.Collectors;
103 
104 
105 public class SubscriptionManagerTest {
106     private static final String TAG = "SubscriptionManagerTest";
107     private static final String MODIFY_PHONE_STATE = "android.permission.MODIFY_PHONE_STATE";
108     private static final String READ_PRIVILEGED_PHONE_STATE =
109             "android.permission.READ_PRIVILEGED_PHONE_STATE";
110     private static final List<Uri> CONTACTS = new ArrayList<>();
111     static {
112         CONTACTS.add(Uri.fromParts("tel", "+16505551212", null));
113         CONTACTS.add(Uri.fromParts("tel", "+16505552323", null));
114     }
115 
116     // time to wait when testing APIs which enable or disable subscriptions. The time waiting
117     // to enable is longer because enabling a subscription can take longer than disabling
118     private static final int SUBSCRIPTION_DISABLE_WAIT_MS = 5000;
119     private static final int SUBSCRIPTION_ENABLE_WAIT_MS = 50000;
120 
121     // time to wait for subscription plans to expire
122     private static final int SUBSCRIPTION_PLAN_EXPIRY_MS = 50;
123     private static final int SUBSCRIPTION_PLAN_CLEAR_WAIT_MS = 5000;
124 
125     private int mSubId;
126     private int mDefaultVoiceSubId;
127     private String mPackageName;
128     private SubscriptionManager mSm;
129     private SubscriptionManagerTest.CarrierConfigReceiver mReceiver;
130 
131     private static class CarrierConfigReceiver extends BroadcastReceiver {
132         private CountDownLatch mLatch = new CountDownLatch(1);
133         private final int mSubId;
134 
CarrierConfigReceiver(int subId)135         CarrierConfigReceiver(int subId) {
136             mSubId = subId;
137         }
138 
139         @Override
onReceive(Context context, Intent intent)140         public void onReceive(Context context, Intent intent) {
141             if (CarrierConfigManager.ACTION_CARRIER_CONFIG_CHANGED.equals(intent.getAction())) {
142                 int subId = intent.getIntExtra(CarrierConfigManager.EXTRA_SUBSCRIPTION_INDEX,
143                         SubscriptionManager.INVALID_SUBSCRIPTION_ID);
144                 if (mSubId == subId) {
145                     mLatch.countDown();
146                 }
147             }
148         }
149 
clearQueue()150         void clearQueue() {
151             mLatch = new CountDownLatch(1);
152         }
153 
waitForCarrierConfigChanged()154         void waitForCarrierConfigChanged() throws Exception {
155             mLatch.await(5000, TimeUnit.MILLISECONDS);
156         }
157     }
158 
overrideCarrierConfig(PersistableBundle bundle, int subId)159     private void overrideCarrierConfig(PersistableBundle bundle, int subId) throws Exception {
160         mReceiver = new CarrierConfigReceiver(subId);
161         IntentFilter filter = new IntentFilter(CarrierConfigManager.ACTION_CARRIER_CONFIG_CHANGED);
162         InstrumentationRegistry.getContext().registerReceiver(mReceiver, filter);
163         try {
164             mReceiver.clearQueue();
165 
166             ShellIdentityUtils.invokeMethodWithShellPermissionsNoReturn(
167                     InstrumentationRegistry.getContext().getSystemService(
168                             CarrierConfigManager.class),
169                     (cm) -> cm.overrideConfig(subId, bundle));
170             mReceiver.waitForCarrierConfigChanged();
171         } finally {
172             InstrumentationRegistry.getContext().unregisterReceiver(mReceiver);
173             mReceiver = null;
174         }
175     }
176 
177     /**
178      * Callback used in testRegisterNetworkCallback that allows caller to block on
179      * {@code onAvailable}.
180      */
181     private static class TestNetworkCallback extends ConnectivityManager.NetworkCallback {
182         private final CountDownLatch mAvailableLatch = new CountDownLatch(1);
183 
waitForAvailable()184         public void waitForAvailable() throws InterruptedException {
185             assertTrue("Cellular network did not come up after 5 seconds",
186                     mAvailableLatch.await(5, TimeUnit.SECONDS));
187         }
188 
189         @Override
onAvailable(Network network)190         public void onAvailable(Network network) {
191             mAvailableLatch.countDown();
192         }
193     }
194 
195     @BeforeClass
setUpClass()196     public static void setUpClass() throws Exception {
197         if (!isSupported()) return;
198 
199         final TestNetworkCallback callback = new TestNetworkCallback();
200         final ConnectivityManager cm = InstrumentationRegistry.getContext()
201                 .getSystemService(ConnectivityManager.class);
202         cm.registerNetworkCallback(new NetworkRequest.Builder()
203                 .addTransportType(TRANSPORT_CELLULAR)
204                 .addCapability(NET_CAPABILITY_INTERNET)
205                 .build(), callback);
206         try {
207             // Wait to get callback for availability of internet
208             callback.waitForAvailable();
209         } catch (InterruptedException e) {
210             fail("NetworkCallback wait was interrupted.");
211         } finally {
212             cm.unregisterNetworkCallback(callback);
213         }
214     }
215 
216     @AfterClass
tearDownClass()217     public static void tearDownClass() throws Exception {
218         if (!isSupported()) return;
219         TelephonyUtils.flushTelephonyMetrics(InstrumentationRegistry.getInstrumentation());
220     }
221 
222     @Before
setUp()223     public void setUp() throws Exception {
224         assumeTrue(isSupported());
225 
226         mSm = InstrumentationRegistry.getContext().getSystemService(SubscriptionManager.class);
227         mSubId = SubscriptionManager.getDefaultDataSubscriptionId();
228         mDefaultVoiceSubId = SubscriptionManager.getDefaultVoiceSubscriptionId();
229         mPackageName = InstrumentationRegistry.getContext().getPackageName();
230 
231         setIdentifierAccess(false);
232     }
233 
234     @After
tearDown()235     public void tearDown() throws Exception {
236         if (mReceiver != null) {
237             InstrumentationRegistry.getContext().unregisterReceiver(mReceiver);
238             mReceiver = null;
239         }
240     }
241 
242     /**
243      * Correctness check that both {@link PackageManager#FEATURE_TELEPHONY} and
244      * {@link NetworkCapabilities#TRANSPORT_CELLULAR} network must both be
245      * either defined or undefined; you can't cross the streams.
246      */
247     @Test
testCorrectness()248     public void testCorrectness() throws Exception {
249         final boolean hasCellular = findCellularNetwork() != null;
250         if (!hasCellular) {
251             fail("Device claims to support " + PackageManager.FEATURE_TELEPHONY
252                     + " but has no active cellular network, which is required for validation");
253         }
254 
255         if (mSubId == SubscriptionManager.INVALID_SUBSCRIPTION_ID) {
256             fail("Device must have a valid default data subId for validation");
257         }
258     }
259 
260     @Test
testGetActiveSubscriptionInfoCount()261     public void testGetActiveSubscriptionInfoCount() throws Exception {
262         assertTrue(mSm.getActiveSubscriptionInfoCount() <=
263                 mSm.getActiveSubscriptionInfoCountMax());
264     }
265 
266     @Test
testGetActiveSubscriptionInfoForIcc()267     public void testGetActiveSubscriptionInfoForIcc() throws Exception {
268         SubscriptionInfo info = ShellIdentityUtils.invokeMethodWithShellPermissions(mSm,
269                 (sm) -> sm.getActiveSubscriptionInfo(mSubId));
270         assertNotNull(ShellIdentityUtils.invokeMethodWithShellPermissions(mSm,
271                 (sm) -> sm.getActiveSubscriptionInfoForIcc(info.getIccId())));
272     }
273 
274     @Test
testGetAllSubscriptionInfoList()275     public void testGetAllSubscriptionInfoList() throws Exception {
276         List<SubscriptionInfo> allSubInfoList = ShellIdentityUtils.invokeMethodWithShellPermissions(
277                 mSm, SubscriptionManager::getAllSubscriptionInfoList);
278         SubscriptionInfo subInfo = ShellIdentityUtils.invokeMethodWithShellPermissions(mSm,
279                 (sm) -> sm.getActiveSubscriptionInfo(mSubId));
280         assertThat(allSubInfoList).contains(subInfo);
281     }
282 
283     @Test
testIsActiveSubscriptionId()284     public void testIsActiveSubscriptionId() throws Exception {
285         assertTrue(mSm.isActiveSubscriptionId(mSubId));
286     }
287 
288     @Test
testGetSubscriptionIds()289     public void testGetSubscriptionIds() throws Exception {
290         int slotId = SubscriptionManager.getSlotIndex(mSubId);
291         int[] subIds = mSm.getSubscriptionIds(slotId);
292         assertNotNull(subIds);
293         assertTrue(ArrayUtils.contains(subIds, mSubId));
294     }
295 
296     @Test
testGetSubscriptionId()297     public void testGetSubscriptionId() throws Exception {
298         int slotId = SubscriptionManager.getSlotIndex(mSubId);
299         assertThat(SubscriptionManager.getSubscriptionId(slotId)).isEqualTo(mSubId);
300     }
301 
302     @Test
testGetResourcesForSubId()303     public void testGetResourcesForSubId() {
304         Resources r = ShellIdentityUtils.invokeMethodWithShellPermissions(mSm,
305                 (sm) -> sm.getResourcesForSubId(InstrumentationRegistry.getContext(), mSubId));
306         // this is an old method which returns mcc/mnc as ints, so use the old SM.getMcc/Mnc methods
307         // because they also use ints
308         assertEquals(mSm.getActiveSubscriptionInfo(mSubId).getMcc(), r.getConfiguration().mcc);
309         assertEquals(mSm.getActiveSubscriptionInfo(mSubId).getMnc(), r.getConfiguration().mnc);
310     }
311 
312     @Test
testIsUsableSubscriptionId()313     public void testIsUsableSubscriptionId() throws Exception {
314         assertTrue(SubscriptionManager.isUsableSubscriptionId(mSubId));
315     }
316 
317     @Test
testActiveSubscriptions()318     public void testActiveSubscriptions() throws Exception {
319         List<SubscriptionInfo> subList = ShellIdentityUtils.invokeMethodWithShellPermissions(mSm,
320                 (sm) -> sm.getActiveSubscriptionInfoList());
321         int[] idList = ShellIdentityUtils.invokeMethodWithShellPermissions(mSm,
322                 (sm) -> sm.getActiveSubscriptionIdList());
323         // Assert when there is no sim card present or detected
324         assertNotNull("Active subscriber required", subList);
325         assertNotNull("Active subscriber required", idList);
326         assertFalse("Active subscriber required", subList.isEmpty());
327         assertNotEquals("Active subscriber required", 0, idList.length);
328         for (int i = 0; i < subList.size(); i++) {
329             assertTrue(subList.get(i).getSubscriptionId() >= 0);
330             assertTrue(subList.get(i).getSimSlotIndex() >= 0);
331             assertTrue(ArrayUtils.contains(idList, subList.get(i).getSubscriptionId()));
332             if (i >= 1) {
333                 assertTrue(subList.get(i - 1).getSimSlotIndex()
334                         <= subList.get(i).getSimSlotIndex());
335                 assertTrue(subList.get(i - 1).getSimSlotIndex() < subList.get(i).getSimSlotIndex()
336                         || subList.get(i - 1).getSubscriptionId()
337                         < subList.get(i).getSubscriptionId());
338             }
339         }
340     }
341 
342     @Test
343     public void testSubscriptionPlans() throws Exception {
344         // Make ourselves the owner
345         setSubPlanOwner(mSubId, mPackageName);
346 
347         // Push empty list and we get empty back
348         mSm.setSubscriptionPlans(mSubId, Arrays.asList());
349         assertEquals(Arrays.asList(), mSm.getSubscriptionPlans(mSubId));
350 
351         // Push simple plan and get it back
352         final SubscriptionPlan plan = buildValidSubscriptionPlan(System.currentTimeMillis());
353         mSm.setSubscriptionPlans(mSubId, Arrays.asList(plan));
354         assertEquals(Arrays.asList(plan), mSm.getSubscriptionPlans(mSubId));
355 
356         // Push plan with expiration time and verify that it expired
357         mSm.setSubscriptionPlans(mSubId, Arrays.asList(plan), SUBSCRIPTION_PLAN_EXPIRY_MS);
358         Thread.sleep(SUBSCRIPTION_PLAN_EXPIRY_MS);
359         Thread.sleep(SUBSCRIPTION_PLAN_CLEAR_WAIT_MS);
360         assertTrue(mSm.getSubscriptionPlans(mSubId).isEmpty());
361 
362         // Now revoke our access
363         setSubPlanOwner(mSubId, null);
364         try {
365             mSm.setSubscriptionPlans(mSubId, Arrays.asList());
366             fail();
367         } catch (SecurityException expected) {
368         }
369         try {
370             mSm.getSubscriptionPlans(mSubId);
371             fail();
372         } catch (SecurityException expected) {
373         }
374     }
375 
376     @Test
377     public void testSubscriptionPlansOverrideCongested() throws Exception {
378         final ConnectivityManager cm = InstrumentationRegistry.getContext()
379                 .getSystemService(ConnectivityManager.class);
380         final Network net = findCellularNetwork();
381         assertNotNull("Active cellular network required", net);
382 
383         // Make ourselves the owner
384         setSubPlanOwner(mSubId, mPackageName);
385 
386         // Missing plans means no overrides
387         mSm.setSubscriptionPlans(mSubId, Arrays.asList());
388         try {
389             mSm.setSubscriptionOverrideCongested(mSubId, true, 0);
390             fail();
391         } catch (SecurityException | IllegalStateException expected) {
392         }
393 
394         // Defining plans means we get to override
395         mSm.setSubscriptionPlans(mSubId,
396                 Arrays.asList(buildValidSubscriptionPlan(System.currentTimeMillis())));
397 
398         // Cellular is uncongested by default
399         assertTrue(cm.getNetworkCapabilities(net).hasCapability(NET_CAPABILITY_NOT_CONGESTED));
400 
401         // Override should make it go congested
402         {
403             final CountDownLatch latch = waitForNetworkCapabilities(net, caps -> {
404                 return !caps.hasCapability(NET_CAPABILITY_NOT_CONGESTED);
405             });
406             mSm.setSubscriptionOverrideCongested(
407                     mSubId, true, TelephonyManager.getAllNetworkTypes(), 0);
408             assertTrue(latch.await(10, TimeUnit.SECONDS));
409         }
410 
411         // Clearing override should make it go uncongested
412         {
413             final CountDownLatch latch = waitForNetworkCapabilities(net, caps -> {
414                 return caps.hasCapability(NET_CAPABILITY_NOT_CONGESTED);
415             });
416             mSm.setSubscriptionOverrideCongested(mSubId, false, 0);
417             assertTrue(latch.await(10, TimeUnit.SECONDS));
418         }
419 
420         // Now revoke our access
421         setSubPlanOwner(mSubId, null);
422         try {
423             mSm.setSubscriptionOverrideCongested(
424                     mSubId, true, TelephonyManager.getAllNetworkTypes(), 0);
425             fail();
426         } catch (SecurityException | IllegalStateException expected) {
427         }
428     }
429 
430     @Test
testSubscriptionInfoRecord()431     public void testSubscriptionInfoRecord() {
432         if (!isAutomotive()) return;
433 
434         UiAutomation uiAutomation = InstrumentationRegistry.getInstrumentation().getUiAutomation();
435 
436         final String uniqueId = "00:01:02:03:04:05";
437         final String displayName = "device_name";
438         uiAutomation.adoptShellPermissionIdentity();
439         try {
440             mSm.addSubscriptionInfoRecord(uniqueId, displayName, 0,
441                     SubscriptionManager.SUBSCRIPTION_TYPE_REMOTE_SIM);
442             assertNotNull(mSm.getActiveSubscriptionInfoForIcc(uniqueId));
443             mSm.removeSubscriptionInfoRecord(uniqueId,
444                     SubscriptionManager.SUBSCRIPTION_TYPE_REMOTE_SIM);
445             assertNull(mSm.getActiveSubscriptionInfoForIcc(uniqueId));
446         } finally {
447             uiAutomation.dropShellPermissionIdentity();
448         }
449 
450         // Testing permission fail
451         try {
452             mSm.addSubscriptionInfoRecord(uniqueId, displayName, 0,
453                     SubscriptionManager.SUBSCRIPTION_TYPE_REMOTE_SIM);
454             mSm.removeSubscriptionInfoRecord(uniqueId,
455                     SubscriptionManager.SUBSCRIPTION_TYPE_REMOTE_SIM);
456             fail("SecurityException should be thrown without MODIFY_PHONE_STATE");
457         } catch (SecurityException expected) {
458             // expected
459         }
460 
461     }
462 
463     @Test
testSetDefaultVoiceSubId()464     public void testSetDefaultVoiceSubId() {
465         int oldSubId = SubscriptionManager.getDefaultVoiceSubscriptionId();
466         InstrumentationRegistry.getInstrumentation().getUiAutomation()
467                 .adoptShellPermissionIdentity();
468         try {
469             mSm.setDefaultVoiceSubscriptionId(SubscriptionManager.INVALID_SUBSCRIPTION_ID);
470             assertEquals(SubscriptionManager.INVALID_SUBSCRIPTION_ID,
471                     SubscriptionManager.getDefaultVoiceSubscriptionId());
472             mSm.setDefaultVoiceSubscriptionId(oldSubId);
473             assertEquals(oldSubId, SubscriptionManager.getDefaultVoiceSubscriptionId());
474         } finally {
475             InstrumentationRegistry.getInstrumentation().getUiAutomation()
476                     .dropShellPermissionIdentity();
477         }
478     }
479 
480     @Test
testSubscriptionPlansOverrideUnmetered()481     public void testSubscriptionPlansOverrideUnmetered() throws Exception {
482         final ConnectivityManager cm = InstrumentationRegistry.getContext()
483                 .getSystemService(ConnectivityManager.class);
484         final Network net = findCellularNetwork();
485         assertNotNull("Active cellular network required", net);
486 
487         // TODO: Remove this check after b/176119724 is fixed.
488         if (!isUnmetered5GSupported()) return;
489 
490         // Cellular is metered by default
491         assertFalse(cm.getNetworkCapabilities(net).hasCapability(
492                 NET_CAPABILITY_TEMPORARILY_NOT_METERED));
493 
494         // Override should make it go temporarily unmetered
495         {
496             final CountDownLatch latch = waitForNetworkCapabilities(net, caps -> {
497                 return caps.hasCapability(NET_CAPABILITY_TEMPORARILY_NOT_METERED);
498             });
499             mSm.setSubscriptionOverrideUnmetered(
500                     mSubId, true, TelephonyManager.getAllNetworkTypes(), 0);
501             assertTrue(latch.await(10, TimeUnit.SECONDS));
502         }
503 
504         // Clearing override should make it go metered
505         {
506             final CountDownLatch latch = waitForNetworkCapabilities(net, caps -> {
507                 return !caps.hasCapability(NET_CAPABILITY_TEMPORARILY_NOT_METERED);
508             });
509             mSm.setSubscriptionOverrideUnmetered(
510                     mSubId, false, TelephonyManager.getAllNetworkTypes(), 0);
511             assertTrue(latch.await(10, TimeUnit.SECONDS));
512         }
513     }
514 
515     @Test
testSubscriptionPlansUnmetered()516     public void testSubscriptionPlansUnmetered() throws Exception {
517         final ConnectivityManager cm = InstrumentationRegistry.getContext()
518                 .getSystemService(ConnectivityManager.class);
519         final Network net = findCellularNetwork();
520         assertNotNull("Active cellular network required", net);
521 
522         // TODO: Remove this check after b/176119724 is fixed.
523         if (!isUnmetered5GSupported()) return;
524 
525         // Make ourselves the owner and define some plans
526         setSubPlanOwner(mSubId, mPackageName);
527         mSm.setSubscriptionPlans(mSubId,
528                 Arrays.asList(buildValidSubscriptionPlan(System.currentTimeMillis())));
529 
530         // Cellular is metered by default
531         assertFalse(cm.getNetworkCapabilities(net).hasCapability(
532                 NET_CAPABILITY_TEMPORARILY_NOT_METERED));
533 
534         SubscriptionPlan unmeteredPlan = SubscriptionPlan.Builder
535                 .createRecurring(ZonedDateTime.parse("2007-03-14T00:00:00.000Z"),
536                         Period.ofMonths(1))
537                 .setTitle("CTS")
538                 .setDataLimit(SubscriptionPlan.BYTES_UNLIMITED,
539                         SubscriptionPlan.LIMIT_BEHAVIOR_THROTTLED)
540                 .build();
541 
542         // Unmetered plan should make it go unmetered
543         {
544             final CountDownLatch latch = waitForNetworkCapabilities(net, caps -> {
545                 return caps.hasCapability(NET_CAPABILITY_TEMPORARILY_NOT_METERED);
546             });
547             mSm.setSubscriptionPlans(mSubId, Arrays.asList(unmeteredPlan));
548             assertTrue(latch.await(10, TimeUnit.SECONDS));
549         }
550 
551         // Metered plan should make it go metered
552         {
553             final CountDownLatch latch = waitForNetworkCapabilities(net, caps -> {
554                 return !caps.hasCapability(NET_CAPABILITY_TEMPORARILY_NOT_METERED);
555             });
556             mSm.setSubscriptionPlans(mSubId,
557                     Arrays.asList(buildValidSubscriptionPlan(System.currentTimeMillis())));
558             assertTrue(latch.await(10, TimeUnit.SECONDS));
559         }
560     }
561 
562     @Test
testSubscriptionPlansInvalid()563     public void testSubscriptionPlansInvalid() throws Exception {
564         // Make ourselves the owner
565         setSubPlanOwner(mSubId, mPackageName);
566 
567         // Empty plans can't override
568         assertOverrideFails();
569 
570         // Nonrecurring plan in the past can't override
571         assertOverrideFails(SubscriptionPlan.Builder
572                 .createNonrecurring(ZonedDateTime.now().minusDays(14),
573                         ZonedDateTime.now().minusDays(7))
574                 .setTitle("CTS")
575                 .setDataLimit(1_000_000_000, SubscriptionPlan.LIMIT_BEHAVIOR_DISABLED)
576                 .build());
577 
578         // Plan with undefined limit can't override
579         assertOverrideFails(SubscriptionPlan.Builder
580                 .createRecurring(ZonedDateTime.parse("2007-03-14T00:00:00.000Z"),
581                         Period.ofMonths(1))
582                 .setTitle("CTS")
583                 .build());
584 
585         // We can override when there is an active plan somewhere
586         final SubscriptionPlan older = SubscriptionPlan.Builder
587                 .createNonrecurring(ZonedDateTime.now().minusDays(14),
588                         ZonedDateTime.now().minusDays(7))
589                 .setTitle("CTS")
590                 .setDataLimit(1_000_000_000, SubscriptionPlan.LIMIT_BEHAVIOR_DISABLED)
591                 .build();
592         final SubscriptionPlan newer = SubscriptionPlan.Builder
593                 .createNonrecurring(ZonedDateTime.now().minusDays(7),
594                         ZonedDateTime.now().plusDays(7))
595                 .setTitle("CTS")
596                 .setDataLimit(1_000_000_000, SubscriptionPlan.LIMIT_BEHAVIOR_DISABLED)
597                 .build();
598         assertOverrideSuccess(older, newer);
599     }
600 
601     @Test
testSubscriptionPlansNetworkTypeValidation()602     public void testSubscriptionPlansNetworkTypeValidation() throws Exception {
603         // Make ourselves the owner
604         setSubPlanOwner(mSubId, mPackageName);
605 
606         // Error when adding 2 plans with the same network type
607         List<SubscriptionPlan> plans = new ArrayList<>();
608         plans.add(buildValidSubscriptionPlan(System.currentTimeMillis()));
609         plans.add(SubscriptionPlan.Builder
610                 .createRecurring(ZonedDateTime.parse("2007-03-14T00:00:00.000Z"),
611                         Period.ofMonths(1))
612                 .setTitle("CTS")
613                 .setNetworkTypes(new int[] {TelephonyManager.NETWORK_TYPE_LTE})
614                 .build());
615         plans.add(SubscriptionPlan.Builder
616                 .createRecurring(ZonedDateTime.parse("2007-03-14T00:00:00.000Z"),
617                         Period.ofMonths(1))
618                 .setTitle("CTS")
619                 .setNetworkTypes(new int[] {TelephonyManager.NETWORK_TYPE_LTE})
620                 .build());
621         try {
622             mSm.setSubscriptionPlans(mSubId, plans);
623             fail();
624         } catch (IllegalArgumentException expected) {
625         }
626 
627         // Error when there is no general plan
628         plans.clear();
629         plans.add(SubscriptionPlan.Builder
630                 .createRecurring(ZonedDateTime.parse("2007-03-14T00:00:00.000Z"),
631                         Period.ofMonths(1))
632                 .setTitle("CTS")
633                 .setNetworkTypes(new int[] {TelephonyManager.NETWORK_TYPE_LTE})
634                 .build());
635         try {
636             mSm.setSubscriptionPlans(mSubId, plans);
637             fail();
638         } catch (IllegalArgumentException expected) {
639         }
640     }
641 
642     @Test
testSubscriptionPlanResetNetworkTypes()643     public void testSubscriptionPlanResetNetworkTypes() {
644         long time = System.currentTimeMillis();
645         SubscriptionPlan plan = SubscriptionPlan.Builder
646                 .createRecurring(ZonedDateTime.parse("2007-03-14T00:00:00.000Z"),
647                         Period.ofMonths(1))
648                 .setTitle("CTS")
649                 .setNetworkTypes(new int[] {TelephonyManager.NETWORK_TYPE_LTE})
650                 .setDataLimit(1_000_000_000, SubscriptionPlan.LIMIT_BEHAVIOR_DISABLED)
651                 .setDataUsage(500_000_000, time)
652                 .resetNetworkTypes()
653                 .build();
654         assertEquals(plan, buildValidSubscriptionPlan(time));
655     }
656 
657     @Test
testSubscriptionGrouping()658     public void testSubscriptionGrouping() throws Exception {
659         // Set subscription group with current sub Id. This should fail
660         // because we don't have MODIFY_PHONE_STATE or carrier privilege permission.
661         List<Integer> subGroup = new ArrayList();
662         subGroup.add(mSubId);
663         try {
664             mSm.createSubscriptionGroup(subGroup);
665             fail();
666         } catch (SecurityException expected) {
667         }
668 
669         // Getting subscriptions in group should return null as setSubscriptionGroup
670         // should fail.
671         SubscriptionInfo info = mSm.getActiveSubscriptionInfo(mSubId);
672         assertNull(info.getGroupUuid());
673 
674         // Remove from subscription group with current sub Id. This should fail
675         // because we don't have MODIFY_PHONE_STATE or carrier privilege permission.
676         try {
677             mSm.addSubscriptionsIntoGroup(subGroup, null);
678             fail();
679         } catch (NullPointerException expected) {
680         }
681 
682         // Add into subscription group that doesn't exist. This should fail
683         // because we don't have MODIFY_PHONE_STATE or carrier privilege permission.
684         try {
685             ParcelUuid groupUuid = new ParcelUuid(UUID.randomUUID());
686             mSm.addSubscriptionsIntoGroup(subGroup, groupUuid);
687             fail();
688         } catch (SecurityException expected) {
689         }
690 
691         // Remove from subscription group with current sub Id. This should fail
692         // because we don't have MODIFY_PHONE_STATE or carrier privilege permission.
693         try {
694             mSm.removeSubscriptionsFromGroup(subGroup, null);
695             fail();
696         } catch (NullPointerException expected) {
697         }
698     }
699 
700     @Test
701     @ApiTest(apis = "android.telephony.SubscriptionManager#getSubscriptionsInGroup")
testSubscriptionGroupingWithPermission()702     public void testSubscriptionGroupingWithPermission() throws Exception {
703         // Set subscription group with current sub Id.
704         List<Integer> subGroup = new ArrayList();
705         subGroup.add(mSubId);
706         ParcelUuid uuid = ShellIdentityUtils.invokeMethodWithShellPermissions(mSm,
707                 (sm) -> sm.createSubscriptionGroup(subGroup));
708 
709         // Getting subscriptions in group.
710         List<SubscriptionInfo> infoList;
711         try {
712             mSm.getSubscriptionsInGroup(uuid);
713             fail("SecurityException should be thrown without device identifiers");
714         } catch (SecurityException ex) {
715             // Expected
716         }
717 
718         // has the READ_PRIVILEGED_PHONE_STATE permission
719         setIdentifierAccess(true);
720         try {
721             infoList = ShellIdentityUtils.invokeMethodWithShellPermissions(mSm,
722                 (sm) -> sm.getSubscriptionsInGroup(uuid), READ_PRIVILEGED_PHONE_STATE);
723         } finally {
724             setIdentifierAccess(false);
725         }
726         assertNotNull(infoList);
727         assertEquals(1, infoList.size());
728         assertEquals(uuid, infoList.get(0).getGroupUuid());
729 
730         infoList = ShellIdentityUtils.invokeMethodWithShellPermissions(mSm,
731                 (sm) -> sm.getSubscriptionsInGroup(uuid));
732         assertNotNull(infoList);
733         assertEquals(1, infoList.size());
734         assertEquals(uuid, infoList.get(0).getGroupUuid());
735 
736         List<SubscriptionInfo> availableInfoList;
737         try {
738             mSm.getAvailableSubscriptionInfoList();
739             fail("SecurityException should be thrown without READ_PRIVILEGED_PHONE_STATE");
740         } catch (SecurityException ex) {
741             // Ignore
742         }
743         availableInfoList = ShellIdentityUtils.invokeMethodWithShellPermissions(mSm,
744                 (sm) -> sm.getAvailableSubscriptionInfoList());
745         // has the OPSTR_READ_DEVICE_IDENTIFIERS permission
746         setIdentifierAccess(true);
747         try {
748             if (availableInfoList.size() > 1) {
749                 List<Integer> availableSubGroup = availableInfoList.stream()
750                         .map(info -> info.getSubscriptionId())
751                         .filter(subId -> subId != mSubId)
752                         .collect(Collectors.toList());
753 
754                 ShellIdentityUtils.invokeMethodWithShellPermissionsNoReturn(mSm,
755                         (sm) -> sm.addSubscriptionsIntoGroup(availableSubGroup, uuid));
756 
757                 infoList = mSm.getSubscriptionsInGroup(uuid);
758                 assertNotNull(infoList);
759                 assertEquals(availableInfoList.size(), infoList.size());
760 
761                 ShellIdentityUtils.invokeMethodWithShellPermissionsNoReturn(mSm,
762                         (sm) -> sm.removeSubscriptionsFromGroup(availableSubGroup, uuid));
763             }
764 
765             // Remove from subscription group with current sub Id.
766             ShellIdentityUtils.invokeMethodWithShellPermissionsNoReturn(mSm,
767                     (sm) -> sm.removeSubscriptionsFromGroup(subGroup, uuid));
768 
769             infoList = mSm.getSubscriptionsInGroup(uuid);
770             assertNotNull(infoList);
771             assertTrue(infoList.isEmpty());
772         } finally {
773             setIdentifierAccess(false);
774         }
775     }
776 
777     @Test
778     @ApiTest(apis = "android.telephony.SubscriptionManager#getSubscriptionsInGroup")
testAddSubscriptionIntoNewGroupWithPermission()779     public void testAddSubscriptionIntoNewGroupWithPermission() throws Exception {
780         // Set subscription group with current sub Id.
781         List<Integer> subGroup = new ArrayList();
782         subGroup.add(mSubId);
783         ParcelUuid uuid = new ParcelUuid(UUID.randomUUID());
784         ShellIdentityUtils.invokeMethodWithShellPermissionsNoReturn(mSm,
785                 (sm) -> sm.addSubscriptionsIntoGroup(subGroup, uuid));
786 
787         List<SubscriptionInfo> infoList;
788         try {
789             mSm.getSubscriptionsInGroup(uuid);
790             fail("SecurityException should be thrown without device identifiers");
791         } catch (SecurityException ex) {
792             // Expected
793         }
794 
795         // Getting subscriptions in group.
796         try {
797             setIdentifierAccess(true);
798             infoList = mSm.getSubscriptionsInGroup(uuid);
799             assertNotNull(infoList);
800             assertEquals(1, infoList.size());
801             assertEquals(uuid, infoList.get(0).getGroupUuid());
802 
803             // Remove from subscription group with current sub Id.
804             ShellIdentityUtils.invokeMethodWithShellPermissionsNoReturn(mSm,
805                     (sm) -> sm.removeSubscriptionsFromGroup(subGroup, uuid));
806 
807             infoList = ShellIdentityUtils.invokeMethodWithShellPermissions(mSm,
808                     (sm) -> sm.getSubscriptionsInGroup(uuid));
809             assertNotNull(infoList);
810             assertTrue(infoList.isEmpty());
811         } finally {
812             setIdentifierAccess(false);
813         }
814     }
815 
816     @Test
817     @ApiTest(apis = "android.telephony.SubscriptionManager#setOpportunistic")
testSettingOpportunisticSubscription()818     public void testSettingOpportunisticSubscription() throws Exception {
819         // Set subscription to be opportunistic. This should fail
820         // because we don't have MODIFY_PHONE_STATE or carrier privilege permission.
821         try {
822             mSm.setOpportunistic(true, mSubId);
823             fail();
824         } catch (SecurityException expected) {
825         }
826 
827         // Shouldn't crash.
828         SubscriptionInfo info = mSm.getActiveSubscriptionInfo(mSubId);
829         info.isOpportunistic();
830     }
831 
832     @Test
testMccMncString()833     public void testMccMncString() {
834         SubscriptionInfo info = mSm.getActiveSubscriptionInfo(mSubId);
835         String mcc = info.getMccString();
836         String mnc = info.getMncString();
837         assertTrue(mcc == null || mcc.length() <= 3);
838         assertTrue(mnc == null || mnc.length() <= 3);
839     }
840 
841     @Test
testSetUiccApplicationsEnabled()842     public void testSetUiccApplicationsEnabled() throws Exception {
843         boolean canDisable = ShellIdentityUtils.invokeMethodWithShellPermissions(mSm,
844                 (sm) -> sm.canDisablePhysicalSubscription());
845         if (canDisable) {
846             Object lock = new Object();
847             AtomicBoolean functionCallCompleted = new AtomicBoolean(false);
848             // enabled starts off as true
849             AtomicBoolean valueToWaitFor = new AtomicBoolean(false);
850             TestThread t = new TestThread(new Runnable() {
851                 @Override
852                 public void run() {
853                     Looper.prepare();
854 
855                     SubscriptionManager.OnSubscriptionsChangedListener listener =
856                             new SubscriptionManager.OnSubscriptionsChangedListener() {
857                                 @Override
858                                 public void onSubscriptionsChanged() {
859                                     if (valueToWaitFor.get() == mSm.getActiveSubscriptionInfo(
860                                             mSubId).areUiccApplicationsEnabled()) {
861                                         synchronized (lock) {
862                                             functionCallCompleted.set(true);
863                                             lock.notifyAll();
864                                         }
865                                     }
866                                 }
867                             };
868                     mSm.addOnSubscriptionsChangedListener(listener);
869 
870                     Looper.loop();
871                 }
872             });
873 
874             // Disable the UICC application and wait until we detect the subscription change to
875             // verify
876             t.start();
877             ShellIdentityUtils.invokeMethodWithShellPermissionsNoReturn(mSm,
878                     (sm) -> sm.setUiccApplicationsEnabled(mSubId, false));
879 
880             synchronized (lock) {
881                 if (!functionCallCompleted.get()) {
882                     lock.wait(SUBSCRIPTION_DISABLE_WAIT_MS);
883                 }
884             }
885             if (!functionCallCompleted.get()) {
886                 fail("testSetUiccApplicationsEnabled was not able to disable the UICC app on time");
887             }
888 
889             // Enable the UICC application and wait again
890             functionCallCompleted.set(false);
891             valueToWaitFor.set(true);
892             ShellIdentityUtils.invokeMethodWithShellPermissionsNoReturn(mSm,
893                     (sm) -> sm.setUiccApplicationsEnabled(mSubId, true));
894 
895             synchronized (lock) {
896                 if (!functionCallCompleted.get()) {
897                     lock.wait(SUBSCRIPTION_ENABLE_WAIT_MS);
898                 }
899             }
900             if (!functionCallCompleted.get()) {
901                 fail("testSetUiccApplicationsEnabled was not able to enable to UICC app on time");
902             }
903 
904             // Reset default data and voice subId as it may have been changed as part of the
905             // calls above
906             ShellIdentityUtils.invokeMethodWithShellPermissionsNoReturn(mSm,
907                     (sm) -> sm.setDefaultDataSubId(mSubId));
908             ShellIdentityUtils.invokeMethodWithShellPermissionsNoReturn(mSm,
909                     (sm) -> sm.setDefaultVoiceSubscriptionId(mDefaultVoiceSubId));
910 
911             // Other tests also expect that cellular data must be available if telephony is
912             // supported. Wait for that before returning.
913             final CountDownLatch latch = waitForCellularNetwork();
914             latch.await(10, TimeUnit.SECONDS);
915         }
916     }
917 
918     @Test
testSubscriptionInfoCarrierId()919     public void testSubscriptionInfoCarrierId() {
920         SubscriptionInfo info = mSm.getActiveSubscriptionInfo(mSubId);
921         int carrierId = info.getCarrierId();
922         assertTrue(carrierId >= TelephonyManager.UNKNOWN_CARRIER_ID);
923     }
924 
925     @Test
testGetOpportunisticSubscriptions()926     public void testGetOpportunisticSubscriptions() throws Exception {
927         List<SubscriptionInfo> infoList = mSm.getOpportunisticSubscriptions();
928 
929         for (SubscriptionInfo info : infoList) {
930             assertTrue(info.isOpportunistic());
931         }
932     }
933 
934     @Test
testGetEnabledSubscriptionId()935     public void testGetEnabledSubscriptionId() {
936         int slotId = SubscriptionManager.getSlotIndex(mSubId);
937         if (!SubscriptionManager.isValidSlotIndex(slotId)) {
938             fail("Invalid slot id " + slotId + " for subscription id " + mSubId);
939         }
940         int enabledSubId = executeWithShellPermissionAndDefault(-1, mSm,
941                 (sm) -> sm.getEnabledSubscriptionId(slotId));
942         assertEquals(mSubId, enabledSubId);
943     }
944 
945     @Test
testGetActiveDataSubscriptionId()946     public void testGetActiveDataSubscriptionId() {
947         int activeDataSubIdCurrent = executeWithShellPermissionAndDefault(
948                 SubscriptionManager.INVALID_SUBSCRIPTION_ID, mSm,
949                 (sm) -> sm.getActiveDataSubscriptionId());
950 
951         if (activeDataSubIdCurrent != SubscriptionManager.INVALID_SUBSCRIPTION_ID) {
952             List<SubscriptionInfo> subscriptionInfos = mSm.getCompleteActiveSubscriptionInfoList();
953             boolean foundSub = subscriptionInfos.stream()
954                     .anyMatch(x -> x.getSubscriptionId() == activeDataSubIdCurrent);
955             assertTrue(foundSub);
956         }
957     }
958 
959     @Test
testSetPreferredDataSubscriptionId()960     public void testSetPreferredDataSubscriptionId() {
961         int preferredSubId = executeWithShellPermissionAndDefault(-1, mSm,
962                 (sm) -> sm.getPreferredDataSubscriptionId());
963         if (preferredSubId != SubscriptionManager.DEFAULT_SUBSCRIPTION_ID) {
964             // Make sure to switch back to primary/default data sub first.
965             setPreferredDataSubId(SubscriptionManager.DEFAULT_SUBSCRIPTION_ID);
966         }
967 
968         List<SubscriptionInfo> subscriptionInfos = mSm.getCompleteActiveSubscriptionInfoList();
969 
970         for (SubscriptionInfo subInfo : subscriptionInfos) {
971             // Only test on opportunistic subscriptions.
972             if (!subInfo.isOpportunistic()) continue;
973             setPreferredDataSubId(subInfo.getSubscriptionId());
974         }
975 
976         // Switch data back to previous preferredSubId.
977         setPreferredDataSubId(preferredSubId);
978     }
979 
980     @Test
testRestoreAllSimSpecificSettingsFromBackup()981     public void testRestoreAllSimSpecificSettingsFromBackup() throws Throwable {
982         int activeDataSubId = SubscriptionManager.getActiveDataSubscriptionId();
983         assertNotEquals(activeDataSubId, SubscriptionManager.INVALID_SUBSCRIPTION_ID);
984         SubscriptionInfo activeSubInfo = ShellIdentityUtils.invokeMethodWithShellPermissions(mSm,
985                 (sm) -> sm.getActiveSubscriptionInfo(activeDataSubId));
986         String isoCountryCode = activeSubInfo.getCountryIso();
987 
988         byte[] backupData = ShellIdentityUtils.invokeMethodWithShellPermissions(mSm,
989                 SubscriptionManager::getAllSimSpecificSettingsForBackup);
990         assertTrue(backupData.length > 0);
991 
992         PersistableBundle bundle = new PersistableBundle();
993         bundle.putBoolean(CarrierConfigManager.KEY_EDITABLE_ENHANCED_4G_LTE_BOOL, true);
994         bundle.putBoolean(CarrierConfigManager.KEY_HIDE_ENHANCED_4G_LTE_BOOL, false);
995 
996         overrideCarrierConfig(bundle, activeDataSubId);
997         try {
998             // Get the original ims values.
999             ImsManager imsManager = InstrumentationRegistry.getContext().getSystemService(
1000                     ImsManager.class);
1001             ImsMmTelManager mMmTelManager = imsManager.getImsMmTelManager(activeDataSubId);
1002             boolean isVolteVtEnabledOriginal = ShellIdentityUtils.invokeMethodWithShellPermissions(
1003                     mMmTelManager, ImsMmTelManager::isAdvancedCallingSettingEnabled);
1004             boolean isVtImsEnabledOriginal = ShellIdentityUtils.invokeMethodWithShellPermissions(
1005                     mMmTelManager, ImsMmTelManager::isVtSettingEnabled);
1006             boolean isVoWiFiSettingEnabledOriginal =
1007                     ShellIdentityUtils.invokeMethodWithShellPermissions(
1008                             mMmTelManager, ImsMmTelManager::isVoWiFiSettingEnabled);
1009             int voWifiModeOriginal = ShellIdentityUtils.invokeMethodWithShellPermissions(
1010                     mMmTelManager, ImsMmTelManager::getVoWiFiModeSetting);
1011             int voWiFiRoamingModeOriginal = ShellIdentityUtils.invokeMethodWithShellPermissions(
1012                     mMmTelManager, ImsMmTelManager::getVoWiFiRoamingModeSetting);
1013 
1014             // Get the original RcsUce values.
1015             ImsRcsManager imsRcsManager = imsManager.getImsRcsManager(activeDataSubId);
1016             RcsUceAdapter rcsUceAdapter = imsRcsManager.getUceAdapter();
1017             boolean isImsRcsUceEnabledOriginal =
1018                     ShellIdentityUtils.invokeThrowableMethodWithShellPermissions(
1019                     rcsUceAdapter, RcsUceAdapter::isUceSettingEnabled, ImsException.class,
1020                     android.Manifest.permission.READ_PHONE_STATE);
1021 
1022             //Change values in DB.
1023             ShellIdentityUtils.invokeMethodWithShellPermissionsNoReturn(mMmTelManager,
1024                     (m) -> m.setAdvancedCallingSettingEnabled(!isVolteVtEnabledOriginal));
1025             ShellIdentityUtils.invokeMethodWithShellPermissionsNoReturn(mMmTelManager,
1026                     (m) -> m.setVtSettingEnabled(!isVtImsEnabledOriginal));
1027             ShellIdentityUtils.invokeThrowableMethodWithShellPermissionsNoReturn(
1028                     rcsUceAdapter, (a) -> a.setUceSettingEnabled(!isImsRcsUceEnabledOriginal),
1029                     ImsException.class);
1030             ShellIdentityUtils.invokeMethodWithShellPermissionsNoReturn(mMmTelManager,
1031                     (m) -> m.setVoWiFiSettingEnabled(!isVoWiFiSettingEnabledOriginal));
1032             ShellIdentityUtils.invokeMethodWithShellPermissionsNoReturn(mMmTelManager,
1033                     (m) -> m.setVoWiFiModeSetting((voWifiModeOriginal + 1) % 3));
1034             ShellIdentityUtils.invokeMethodWithShellPermissionsNoReturn(mMmTelManager,
1035                     (m) -> m.setVoWiFiRoamingModeSetting((voWiFiRoamingModeOriginal + 1) % 3));
1036 
1037             // Restore back to original values.
1038             ShellIdentityUtils.invokeMethodWithShellPermissionsNoReturn(mSm,
1039                     (sm) -> sm.restoreAllSimSpecificSettingsFromBackup(backupData));
1040 
1041             final long maxWaitMillis = 5000;
1042             try {
1043                 waitForSubscriptionCondition(
1044                         () -> isVolteVtEnabledOriginal == isAdvancedCallingSettingEnabled(mSubId),
1045                         maxWaitMillis);
1046                 assertEquals(isVolteVtEnabledOriginal, isAdvancedCallingSettingEnabled(mSubId));
1047             } finally {
1048                 overrideCarrierConfig(null, mSubId);
1049             }
1050 
1051             // Get ims values to verify with.
1052             boolean isVolteVtEnabledAfterRestore =
1053                     ShellIdentityUtils.invokeMethodWithShellPermissions(
1054                             mMmTelManager, ImsMmTelManager::isAdvancedCallingSettingEnabled);
1055             boolean isVtImsEnabledAfterRestore =
1056                     ShellIdentityUtils.invokeMethodWithShellPermissions(
1057                             mMmTelManager, ImsMmTelManager::isVtSettingEnabled);
1058             boolean isVoWiFiSettingEnabledAfterRestore =
1059                     ShellIdentityUtils.invokeMethodWithShellPermissions(
1060                             mMmTelManager, ImsMmTelManager::isVoWiFiSettingEnabled);
1061             int voWifiModeAfterRestore = ShellIdentityUtils.invokeMethodWithShellPermissions(
1062                     mMmTelManager, ImsMmTelManager::getVoWiFiModeSetting);
1063             int voWiFiRoamingModeAfterRestore = ShellIdentityUtils.invokeMethodWithShellPermissions(
1064                     mMmTelManager, ImsMmTelManager::getVoWiFiRoamingModeSetting);
1065             // Get RcsUce values to verify with.
1066             boolean isImsRcsUceEnabledAfterRestore =
1067                     ShellIdentityUtils.invokeThrowableMethodWithShellPermissions(
1068                             rcsUceAdapter, RcsUceAdapter::isUceSettingEnabled, ImsException.class,
1069                             android.Manifest.permission.READ_PHONE_STATE);
1070 
1071             assertEquals(isVolteVtEnabledOriginal, isVolteVtEnabledAfterRestore);
1072             if (isoCountryCode == null
1073                     || isoCountryCode.equals("us")
1074                     || isoCountryCode.equals("ca")) {
1075                 assertEquals(!isVoWiFiSettingEnabledOriginal, isVoWiFiSettingEnabledAfterRestore);
1076             } else {
1077                 assertEquals(isVoWiFiSettingEnabledOriginal, isVoWiFiSettingEnabledAfterRestore);
1078             }
1079             assertEquals(voWifiModeOriginal, voWifiModeAfterRestore);
1080             assertEquals(voWiFiRoamingModeOriginal, voWiFiRoamingModeAfterRestore);
1081             assertEquals(isVtImsEnabledOriginal, isVtImsEnabledAfterRestore);
1082             assertEquals(isImsRcsUceEnabledOriginal, isImsRcsUceEnabledAfterRestore);
1083         } finally {
1084             // restore original carrier config.
1085             overrideCarrierConfig(null, activeDataSubId);
1086         }
1087 
1088 
1089         try {
1090             // Check api call will fail without proper permissions.
1091             mSm.restoreAllSimSpecificSettingsFromBackup(backupData);
1092             fail("SecurityException expected");
1093         } catch (SecurityException e) {
1094             // expected
1095         }
1096     }
1097 
1098     @Test
testSetAndGetD2DStatusSharing()1099     public void testSetAndGetD2DStatusSharing() {
1100         UiAutomation uiAutomation = InstrumentationRegistry.getInstrumentation().getUiAutomation();
1101         uiAutomation.adoptShellPermissionIdentity(MODIFY_PHONE_STATE);
1102         try {
1103             int originalD2DStatusSharing = mSm.getDeviceToDeviceStatusSharingPreference(mSubId);
1104             mSm.setDeviceToDeviceStatusSharingPreference(mSubId,
1105                     SubscriptionManager.D2D_SHARING_ALL_CONTACTS);
1106             assertEquals(SubscriptionManager.D2D_SHARING_ALL_CONTACTS,
1107                     mSm.getDeviceToDeviceStatusSharingPreference(mSubId));
1108             mSm.setDeviceToDeviceStatusSharingPreference(
1109                     mSubId, SubscriptionManager.D2D_SHARING_ALL);
1110             assertEquals(SubscriptionManager.D2D_SHARING_ALL,
1111                     mSm.getDeviceToDeviceStatusSharingPreference(mSubId));
1112             mSm.setDeviceToDeviceStatusSharingPreference(mSubId, originalD2DStatusSharing);
1113         } finally {
1114             uiAutomation.dropShellPermissionIdentity();
1115         }
1116     }
1117 
1118     @Test
testSetAndGetD2DSharingContacts()1119     public void testSetAndGetD2DSharingContacts() {
1120         UiAutomation uiAutomation = InstrumentationRegistry.getInstrumentation().getUiAutomation();
1121         uiAutomation.adoptShellPermissionIdentity(MODIFY_PHONE_STATE);
1122         try {
1123             List<Uri> originalD2DSharingContacts =
1124                     mSm.getDeviceToDeviceStatusSharingContacts(mSubId);
1125             mSm.setDeviceToDeviceStatusSharingContacts(mSubId, CONTACTS);
1126             try {
1127                 assertEquals(CONTACTS, mSm.getDeviceToDeviceStatusSharingContacts(mSubId));
1128             } finally {
1129                 mSm.setDeviceToDeviceStatusSharingContacts(mSubId, originalD2DSharingContacts);
1130             }
1131         } finally {
1132             uiAutomation.dropShellPermissionIdentity();
1133         }
1134     }
1135 
1136     @Test
tetsSetAndGetPhoneNumber()1137     public void tetsSetAndGetPhoneNumber() throws Exception {
1138         // The phone number may be anything depends on the state of SIM and device.
1139         // Simply call the getter and make sure no exception.
1140 
1141         // Getters accessiable with READ_PRIVILEGED_PHONE_STATE
1142         InstrumentationRegistry.getInstrumentation().getUiAutomation()
1143                 .adoptShellPermissionIdentity(READ_PRIVILEGED_PHONE_STATE);
1144         try {
1145             mSm.getPhoneNumber(mSubId);
1146             mSm.getPhoneNumber(mSubId, SubscriptionManager.PHONE_NUMBER_SOURCE_UICC);
1147             mSm.getPhoneNumber(mSubId, SubscriptionManager.PHONE_NUMBER_SOURCE_CARRIER);
1148             mSm.getPhoneNumber(mSubId, SubscriptionManager.PHONE_NUMBER_SOURCE_IMS);
1149         } finally {
1150             InstrumentationRegistry.getInstrumentation().getUiAutomation()
1151                     .dropShellPermissionIdentity();
1152         }
1153 
1154         // Getters accessiable with READ_PHONE_NUMBERS
1155         InstrumentationRegistry.getInstrumentation().getUiAutomation()
1156                 .adoptShellPermissionIdentity(android.Manifest.permission.READ_PHONE_NUMBERS);
1157         try {
1158             mSm.getPhoneNumber(mSubId);
1159             mSm.getPhoneNumber(mSubId, SubscriptionManager.PHONE_NUMBER_SOURCE_UICC);
1160             mSm.getPhoneNumber(mSubId, SubscriptionManager.PHONE_NUMBER_SOURCE_CARRIER);
1161             mSm.getPhoneNumber(mSubId, SubscriptionManager.PHONE_NUMBER_SOURCE_IMS);
1162         } finally {
1163             InstrumentationRegistry.getInstrumentation().getUiAutomation()
1164                     .dropShellPermissionIdentity();
1165         }
1166 
1167         // Getters and the setter accessiable with carrier privilege
1168         final String carrierNumber = "1234567890";
1169         CarrierPrivilegeUtils.withCarrierPrivileges(
1170                 InstrumentationRegistry.getContext(),
1171                 mSubId,
1172                 () -> {
1173                     mSm.getPhoneNumber(mSubId);
1174                     mSm.getPhoneNumber(mSubId, SubscriptionManager.PHONE_NUMBER_SOURCE_UICC);
1175                     mSm.getPhoneNumber(mSubId, SubscriptionManager.PHONE_NUMBER_SOURCE_IMS);
1176 
1177                     mSm.setCarrierPhoneNumber(mSubId, carrierNumber);
1178                     assertEquals(
1179                             carrierNumber,
1180                             mSm.getPhoneNumber(
1181                                     mSubId, SubscriptionManager.PHONE_NUMBER_SOURCE_CARRIER));
1182                 });
1183 
1184         // Otherwise, getter and setter will hit SecurityException
1185         try {
1186             mSm.getPhoneNumber(mSubId);
1187             fail("Expect SecurityException from getPhoneNumber()");
1188         } catch (SecurityException e) {
1189             // expected
1190         }
1191         try {
1192             mSm.getPhoneNumber(mSubId, SubscriptionManager.PHONE_NUMBER_SOURCE_UICC);
1193             fail("Expect SecurityException from getPhoneNumber()");
1194         } catch (SecurityException e) {
1195             // expected
1196         }
1197         try {
1198             mSm.getPhoneNumber(mSubId, SubscriptionManager.PHONE_NUMBER_SOURCE_IMS);
1199             fail("Expect SecurityException from getPhoneNumber()");
1200         } catch (SecurityException e) {
1201             // expected
1202         }
1203         try {
1204             mSm.getPhoneNumber(mSubId, SubscriptionManager.PHONE_NUMBER_SOURCE_CARRIER);
1205             fail("Expect SecurityException from getPhoneNumber()");
1206         } catch (SecurityException e) {
1207             // expected
1208         }
1209         try {
1210             mSm.setCarrierPhoneNumber(mSubId, "987");
1211             fail("Expect SecurityException from setCarrierPhoneNumber()");
1212         } catch (SecurityException e) {
1213             // expected
1214         }
1215     }
1216 
getSupportedUsageSettings()1217     private Set<Integer> getSupportedUsageSettings() throws Exception {
1218         final Set<Integer> supportedUsageSettings = new HashSet();
1219         final Context context = InstrumentationRegistry.getContext();
1220 
1221         // Vendors can add supported usage settings by adding resources.
1222         try {
1223             int[] usageSettingsFromResource = context.getResources().getIntArray(
1224                 Resources.getSystem().getIdentifier("config_supported_cellular_usage_settings","array","android"));
1225 
1226             for (int setting : usageSettingsFromResource) {
1227                 supportedUsageSettings.add(setting);
1228             }
1229 
1230         } catch (Resources.NotFoundException ignore) {
1231         }
1232 
1233         // For devices shipping with Radio HAL 2.0 and/or non-HAL devices launching with T,
1234         // the usage settings are required to be supported if the rest of the telephony stack
1235         // has support for that mode of operation.
1236         if (PropertyUtil.isVendorApiLevelAtLeast(android.os.Build.VERSION_CODES.TIRAMISU)) {
1237             final PackageManager pm = InstrumentationRegistry.getContext().getPackageManager();
1238 
1239             if (pm.hasSystemFeature(PackageManager.FEATURE_TELEPHONY_DATA)) {
1240                 supportedUsageSettings.add(SubscriptionManager.USAGE_SETTING_DATA_CENTRIC);
1241             }
1242             if (pm.hasSystemFeature(PackageManager.FEATURE_TELEPHONY_CALLING)) {
1243                 supportedUsageSettings.add(SubscriptionManager.USAGE_SETTING_VOICE_CENTRIC);
1244             }
1245         }
1246 
1247         return supportedUsageSettings;
1248     }
1249 
getUsageSetting()1250     private int getUsageSetting() throws Exception {
1251         SubscriptionInfo info = ShellIdentityUtils.invokeMethodWithShellPermissions(mSm,
1252                 (sm) -> sm.getActiveSubscriptionInfo(mSubId));
1253         return info.getUsageSetting();
1254     }
1255 
checkUsageSetting(int inputSetting, boolean isSupported)1256     private void checkUsageSetting(int inputSetting, boolean isSupported) throws Exception {
1257         final int initialSetting = getUsageSetting();
1258 
1259         PersistableBundle bundle = new PersistableBundle();
1260         bundle.putInt(CarrierConfigManager.KEY_CELLULAR_USAGE_SETTING_INT, inputSetting);
1261         overrideCarrierConfig(bundle, mSubId);
1262 
1263         final int newSetting = getUsageSetting();
1264         assertEquals(isSupported ? inputSetting : initialSetting, newSetting);
1265     }
1266 
1267     @Test
testCellularUsageSetting()1268     public void testCellularUsageSetting() throws Exception {
1269         Set<Integer> supportedUsageSettings = getSupportedUsageSettings();
1270 
1271         // If any setting works, default must be allowed.
1272         if (supportedUsageSettings.size() > 0) {
1273             supportedUsageSettings.add(SubscriptionManager.USAGE_SETTING_DEFAULT);
1274         }
1275 
1276         final int[] allUsageSettings = new int[]{
1277                 SubscriptionManager.USAGE_SETTING_UNKNOWN,
1278                 SubscriptionManager.USAGE_SETTING_DEFAULT,
1279                 SubscriptionManager.USAGE_SETTING_VOICE_CENTRIC,
1280                 SubscriptionManager.USAGE_SETTING_DATA_CENTRIC,
1281                 3 /* undefined value */};
1282 
1283         try {
1284             for (int setting : allUsageSettings) {
1285                 checkUsageSetting(setting, supportedUsageSettings.contains(setting));
1286             }
1287         } finally {
1288             overrideCarrierConfig(null, mSubId);
1289         }
1290     }
1291 
getSubscriptionIso(int subId)1292     private String getSubscriptionIso(int subId) {
1293         SubscriptionInfo info = ShellIdentityUtils.invokeMethodWithShellPermissions(mSm,
1294                 (sm) -> sm.getActiveSubscriptionInfo(subId));
1295         return info.getCountryIso();
1296     }
1297 
isAdvancedCallingSettingEnabled(int subId)1298     private boolean isAdvancedCallingSettingEnabled(int subId) {
1299         ImsManager imsManager = InstrumentationRegistry.getContext().getSystemService(
1300                 ImsManager.class);
1301         ImsMmTelManager mMmTelManager = imsManager.getImsMmTelManager(subId);
1302         return ShellIdentityUtils.invokeMethodWithShellPermissions(
1303                 mMmTelManager, ImsMmTelManager::isAdvancedCallingSettingEnabled);
1304     }
1305 
1306     /**
1307      * Monitor the onSubscriptionsChangedListener until a condition is satisfied.
1308      */
waitForSubscriptionCondition( BooleanSupplier condition, long maxWaitMillis)1309     private void waitForSubscriptionCondition(
1310             BooleanSupplier condition, long maxWaitMillis) throws Throwable {
1311         final Object lock = new Object();
1312 
1313         TestThread t = new TestThread(() -> {
1314             Looper.prepare();
1315 
1316             SubscriptionManager.OnSubscriptionsChangedListener listener =
1317                     new SubscriptionManager.OnSubscriptionsChangedListener() {
1318                         @Override
1319                         public void onSubscriptionsChanged() {
1320                             synchronized (lock) {
1321                                 if (condition.getAsBoolean()) {
1322                                     lock.notifyAll();
1323                                     Looper.myLooper().quitSafely();
1324                                 }
1325                             }
1326                         }
1327                     };
1328             mSm.addOnSubscriptionsChangedListener(listener);
1329             try {
1330                 synchronized (lock) {
1331                     if (condition.getAsBoolean()) lock.notifyAll();
1332                 }
1333                 if (!condition.getAsBoolean()) Looper.loop();
1334             } finally {
1335                 mSm.removeOnSubscriptionsChangedListener(listener);
1336             }
1337         });
1338 
1339         synchronized (lock) {
1340             if (condition.getAsBoolean()) return;
1341             t.start();
1342             lock.wait(maxWaitMillis);
1343             t.joinAndCheck(5000);
1344         }
1345     }
1346 
1347     @Test
testCountryIso()1348     public void testCountryIso() throws Throwable {
1349         final String liechtensteinIso = "li";
1350         final String faroeIslandsIso = "fo";
1351 
1352         final TelephonyManager tm = InstrumentationRegistry.getContext()
1353                 .getSystemService(TelephonyManager.class).createForSubscriptionId(mSubId);
1354 
1355         final long maxWaitMillis = 5000;
1356         final String isoUT = liechtensteinIso.equals(getSubscriptionIso(mSubId))
1357                 ? faroeIslandsIso : liechtensteinIso;
1358 
1359         PersistableBundle bundle = new PersistableBundle();
1360         bundle.putString(CarrierConfigManager.KEY_SIM_COUNTRY_ISO_OVERRIDE_STRING, isoUT);
1361         overrideCarrierConfig(bundle, mSubId);
1362         try {
1363             waitForSubscriptionCondition(
1364                     () -> isoUT.equals(getSubscriptionIso(mSubId)),
1365                     maxWaitMillis);
1366 
1367             assertEquals(isoUT, getSubscriptionIso(mSubId));
1368             assertEquals(isoUT, tm.getSimCountryIso());
1369         } finally {
1370             overrideCarrierConfig(null, mSubId);
1371         }
1372     }
1373 
1374     @Nullable
getBundleFromBackupData(byte[] data)1375     private PersistableBundle getBundleFromBackupData(byte[] data) {
1376         try (ByteArrayInputStream bis = new ByteArrayInputStream(data)) {
1377             return PersistableBundle.readFromStream(bis);
1378         } catch (IOException e) {
1379             return null;
1380         }
1381     }
1382 
setPreferredDataSubId(int subId)1383     private void setPreferredDataSubId(int subId) {
1384         final LinkedBlockingQueue<Integer> resultQueue = new LinkedBlockingQueue<>(1);
1385         Executor executor = (command)-> command.run();
1386         Consumer<Integer> consumer = (res)-> {
1387             if (res == null) {
1388                 resultQueue.offer(-1);
1389             } else {
1390                 resultQueue.offer(res);
1391             }
1392         };
1393 
1394         ShellIdentityUtils.invokeMethodWithShellPermissionsNoReturn(mSm,
1395                 (sm) -> sm.setPreferredDataSubscriptionId(subId, false,
1396                         executor, consumer));
1397         int res = -1;
1398         try {
1399             res = resultQueue.poll(2, TimeUnit.SECONDS);
1400         } catch (InterruptedException e) {
1401             fail("Cannot get the modem result in time");
1402         }
1403 
1404         assertEquals(SET_OPPORTUNISTIC_SUB_SUCCESS, res);
1405         int getValue = executeWithShellPermissionAndDefault(-1, mSm,
1406                 (sm) -> sm.getPreferredDataSubscriptionId());
1407         assertEquals(subId, getValue);
1408     }
1409 
executeWithShellPermissionAndDefault(T defaultValue, U targetObject, ShellIdentityUtils.ShellPermissionMethodHelper<T, U> helper)1410     private <T, U> T executeWithShellPermissionAndDefault(T defaultValue, U targetObject,
1411             ShellIdentityUtils.ShellPermissionMethodHelper<T, U> helper) {
1412         try {
1413             return ShellIdentityUtils.invokeMethodWithShellPermissions(targetObject, helper);
1414         } catch (Exception e) {
1415             // do nothing, return default
1416         }
1417         return defaultValue;
1418     }
1419 
assertOverrideSuccess(SubscriptionPlan... plans)1420     private void assertOverrideSuccess(SubscriptionPlan... plans) {
1421         mSm.setSubscriptionPlans(mSubId, Arrays.asList(plans));
1422         mSm.setSubscriptionOverrideCongested(mSubId, false, 0);
1423     }
1424 
assertOverrideFails(SubscriptionPlan... plans)1425     private void assertOverrideFails(SubscriptionPlan... plans) {
1426         mSm.setSubscriptionPlans(mSubId, Arrays.asList(plans));
1427         try {
1428             mSm.setSubscriptionOverrideCongested(mSubId, false, 0);
1429             fail();
1430         } catch (SecurityException | IllegalStateException expected) {
1431         }
1432     }
1433 
waitForNetworkCapabilities(Network network, Predicate<NetworkCapabilities> predicate)1434     public static CountDownLatch waitForNetworkCapabilities(Network network,
1435             Predicate<NetworkCapabilities> predicate) {
1436         final CountDownLatch latch = new CountDownLatch(1);
1437         final ConnectivityManager cm = InstrumentationRegistry.getContext()
1438                 .getSystemService(ConnectivityManager.class);
1439         cm.registerNetworkCallback(new NetworkRequest.Builder().build(),
1440                 new NetworkCallback() {
1441                     @Override
1442                     public void onCapabilitiesChanged(Network net, NetworkCapabilities caps) {
1443                         if (net.equals(network) && predicate.test(caps)) {
1444                             latch.countDown();
1445                             cm.unregisterNetworkCallback(this);
1446                         }
1447                     }
1448                 });
1449         return latch;
1450     }
1451 
1452     /**
1453      * Corresponding to findCellularNetwork()
1454      */
waitForCellularNetwork()1455     private static CountDownLatch waitForCellularNetwork() {
1456         final CountDownLatch latch = new CountDownLatch(1);
1457         final ConnectivityManager cm = InstrumentationRegistry.getContext()
1458                 .getSystemService(ConnectivityManager.class);
1459         cm.registerNetworkCallback(new NetworkRequest.Builder().build(),
1460                 new NetworkCallback() {
1461                     @Override
1462                     public void onCapabilitiesChanged(Network net, NetworkCapabilities caps) {
1463                         if (caps.hasTransport(TRANSPORT_CELLULAR)
1464                                 && caps.hasCapability(NET_CAPABILITY_INTERNET)
1465                                 && caps.hasCapability(NET_CAPABILITY_NOT_RESTRICTED)) {
1466                             latch.countDown();
1467                             cm.unregisterNetworkCallback(this);
1468                         }
1469                     }
1470                 });
1471         return latch;
1472     }
1473 
buildValidSubscriptionPlan(long dataUsageTime)1474     private static SubscriptionPlan buildValidSubscriptionPlan(long dataUsageTime) {
1475         return SubscriptionPlan.Builder
1476                 .createRecurring(ZonedDateTime.parse("2007-03-14T00:00:00.000Z"),
1477                         Period.ofMonths(1))
1478                 .setTitle("CTS")
1479                 .setDataLimit(1_000_000_000, SubscriptionPlan.LIMIT_BEHAVIOR_DISABLED)
1480                 .setDataUsage(500_000_000, dataUsageTime)
1481                 .build();
1482     }
1483 
findCellularNetwork()1484     private static @Nullable Network findCellularNetwork() {
1485         final ConnectivityManager cm = InstrumentationRegistry.getContext()
1486                 .getSystemService(ConnectivityManager.class);
1487         for (Network net : cm.getAllNetworks()) {
1488             final NetworkCapabilities caps = cm.getNetworkCapabilities(net);
1489             if (caps != null && caps.hasTransport(TRANSPORT_CELLULAR)
1490                     && caps.hasCapability(NET_CAPABILITY_INTERNET)
1491                     && caps.hasCapability(NET_CAPABILITY_NOT_RESTRICTED)) {
1492                 return net;
1493             }
1494         }
1495         return null;
1496     }
1497 
isSupported()1498     private static boolean isSupported() {
1499         return InstrumentationRegistry.getContext().getPackageManager().hasSystemFeature(
1500                 PackageManager.FEATURE_TELEPHONY_SUBSCRIPTION);
1501     }
1502 
isAutomotive()1503     private static boolean isAutomotive() {
1504         return InstrumentationRegistry.getContext().getPackageManager()
1505                 .hasSystemFeature(PackageManager.FEATURE_AUTOMOTIVE);
1506     }
1507 
isDSDS()1508     private static boolean isDSDS() {
1509         TelephonyManager tm = InstrumentationRegistry.getContext()
1510                 .getSystemService(TelephonyManager.class);
1511         return tm != null && tm.getPhoneCount() > 1;
1512     }
1513 
setSubPlanOwner(int subId, String packageName)1514     private static void setSubPlanOwner(int subId, String packageName) throws Exception {
1515         SystemUtil.runShellCommand(InstrumentationRegistry.getInstrumentation(),
1516                 "cmd netpolicy set sub-plan-owner " + subId + " " + packageName);
1517     }
1518 
isUnmetered5GSupported()1519     private boolean isUnmetered5GSupported() {
1520         final CarrierConfigManager ccm = InstrumentationRegistry.getContext()
1521                 .getSystemService(CarrierConfigManager.class);
1522         PersistableBundle carrierConfig = ccm.getConfigForSubId(mSubId);
1523 
1524         final TelephonyManager tm = InstrumentationRegistry.getContext()
1525                 .getSystemService(TelephonyManager.class);
1526         int dataNetworkType = tm.getDataNetworkType(mSubId);
1527         long supportedRats = ShellIdentityUtils.invokeMethodWithShellPermissions(tm,
1528                 TelephonyManager::getSupportedRadioAccessFamily);
1529 
1530         boolean validCarrier = carrierConfig.getBoolean(
1531                 CarrierConfigManager.KEY_NETWORK_TEMP_NOT_METERED_SUPPORTED_BOOL);
1532         boolean validCapabilities = (supportedRats & TelephonyManager.NETWORK_TYPE_BITMASK_NR) != 0;
1533         // TODO: need to check for TelephonyDisplayInfo override for NR NSA
1534         boolean validNetworkType = dataNetworkType == TelephonyManager.NETWORK_TYPE_NR;
1535 
1536         return validCarrier && validNetworkType && validCapabilities;
1537     }
1538 
setIdentifierAccess(boolean allowed)1539     private void setIdentifierAccess(boolean allowed) {
1540         CountDownLatch changeLatch = new CountDownLatch(1);
1541         String op = AppOpsManager.OPSTR_READ_DEVICE_IDENTIFIERS;
1542         AppOpsManager appOpsManager = InstrumentationRegistry.getContext().getSystemService(
1543                 AppOpsManager.class);
1544         int mode = allowed ? AppOpsManager.MODE_ALLOWED : AppOpsManager.opToDefaultMode(op);
1545         if (appOpsManager.unsafeCheckOpNoThrow(op, Process.myUid(),
1546                     InstrumentationRegistry.getContext().getOpPackageName()) == mode) {
1547             return;
1548         }
1549         AppOpsManager.OnOpChangedListener opListener =
1550                 (String appOp, String packageName) -> changeLatch.countDown();
1551         appOpsManager.startWatchingMode(op, InstrumentationRegistry.getContext().getOpPackageName(),
1552                 opListener);
1553         try {
1554             ShellIdentityUtils.invokeMethodWithShellPermissionsNoReturn(
1555                     appOpsManager, (appOps) -> appOps.setUidMode(op, Process.myUid(), mode));
1556             changeLatch.await(5000, TimeUnit.MILLISECONDS);
1557         } catch (InterruptedException ie) {
1558             fail("Never received appOp change for Identifier Access");
1559         } finally {
1560             appOpsManager.stopWatchingMode(opListener);
1561         }
1562     }
1563 }
1564