17ed49e5f21cfa57ddc2c34a108aa3d6c8e09013
[android/platform/frameworks/opt/telephony.git] / tests / telephonytests / src / com / android / internal / telephony / dataconnection / DcTrackerTest.java
1 /*
2  * Copyright (C) 2016 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 com.android.internal.telephony.dataconnection;
18
19 import static com.android.internal.telephony.TelephonyTestUtils.waitForMs;
20
21 import static org.junit.Assert.assertArrayEquals;
22 import static org.junit.Assert.assertEquals;
23 import static org.junit.Assert.assertFalse;
24 import static org.junit.Assert.assertTrue;
25 import static org.junit.Assert.fail;
26 import static org.mockito.Matchers.any;
27 import static org.mockito.Matchers.anyInt;
28 import static org.mockito.Matchers.anyLong;
29 import static org.mockito.Matchers.anyString;
30 import static org.mockito.Matchers.eq;
31 import static org.mockito.Mockito.doAnswer;
32 import static org.mockito.Mockito.doReturn;
33 import static org.mockito.Mockito.never;
34 import static org.mockito.Mockito.times;
35 import static org.mockito.Mockito.verify;
36
37 import android.app.AlarmManager;
38 import android.app.PendingIntent;
39 import android.content.ContentResolver;
40 import android.content.Context;
41 import android.content.Intent;
42 import android.database.Cursor;
43 import android.database.MatrixCursor;
44 import android.net.LinkProperties;
45 import android.net.NetworkCapabilities;
46 import android.net.NetworkRequest;
47 import android.net.Uri;
48 import android.os.AsyncResult;
49 import android.os.HandlerThread;
50 import android.os.IBinder;
51 import android.os.Message;
52 import android.os.PersistableBundle;
53 import android.provider.Settings;
54 import android.provider.Telephony;
55 import android.support.test.filters.FlakyTest;
56 import android.telephony.CarrierConfigManager;
57 import android.telephony.ServiceState;
58 import android.telephony.SubscriptionInfo;
59 import android.telephony.SubscriptionManager;
60 import android.test.mock.MockContentProvider;
61 import android.test.mock.MockContentResolver;
62 import android.test.suitebuilder.annotation.MediumTest;
63 import android.util.LocalLog;
64
65 import com.android.internal.telephony.DctConstants;
66 import com.android.internal.telephony.ISub;
67 import com.android.internal.telephony.Phone;
68 import com.android.internal.telephony.PhoneConstants;
69 import com.android.internal.telephony.TelephonyTest;
70 import com.android.internal.telephony.TestApplication;
71 import com.android.internal.telephony.dataconnection.DcTracker.DataAllowFailReason;
72
73 import org.junit.After;
74 import org.junit.Before;
75 import org.junit.Test;
76 import org.mockito.ArgumentCaptor;
77 import org.mockito.Mock;
78 import org.mockito.invocation.InvocationOnMock;
79 import org.mockito.stubbing.Answer;
80
81 import java.lang.reflect.Method;
82 import java.util.Arrays;
83 import java.util.List;
84 import java.util.regex.Matcher;
85 import java.util.regex.Pattern;
86
87 public class DcTrackerTest extends TelephonyTest {
88
89     private final static String[] sNetworkAttributes = new String[]{
90             "mobile,0,0,0,-1,true", "mobile_mms,2,0,2,60000,true",
91             "mobile_supl,3,0,2,60000,true", "mobile_dun,4,0,2,60000,true",
92             "mobile_hipri,5,0,3,60000,true", "mobile_fota,10,0,2,60000,true",
93             "mobile_ims,11,0,2,60000,true", "mobile_cbs,12,0,2,60000,true",
94             "mobile_ia,14,0,2,-1,true", "mobile_emergency,15,0,2,-1,true"};
95
96     private final static List<String> sApnTypes = Arrays.asList(
97             "default", "mms", "cbs", "fota", "supl", "ia", "emergency", "dun", "hipri", "ims");
98
99     public static final String FAKE_APN1 = "FAKE APN 1";
100     public static final String FAKE_APN2 = "FAKE APN 2";
101     public static final String FAKE_APN3 = "FAKE APN 3";
102     public static final String FAKE_IFNAME = "FAKE IFNAME";
103     public static final String FAKE_PCSCF_ADDRESS = "22.33.44.55";
104     public static final String FAKE_GATEWAY = "11.22.33.44";
105     public static final String FAKE_DNS = "55.66.77.88";
106     public static final String FAKE_ADDRESS = "99.88.77.66";
107
108     @Mock
109     ISub mIsub;
110     @Mock
111     IBinder mBinder;
112     @Mock
113     NetworkRequest mNetworkRequest;
114     @Mock
115     SubscriptionInfo mSubscriptionInfo;
116
117     private DcTracker mDct;
118     private DcTrackerTestHandler mDcTrackerTestHandler;
119
120     private AlarmManager mAlarmManager;
121
122     private PersistableBundle mBundle;
123
124     private SubscriptionManager.OnSubscriptionsChangedListener mOnSubscriptionsChangedListener;
125
126     private final ApnSettingContentProvider mApnSettingContentProvider =
127             new ApnSettingContentProvider();
128
129     private class DcTrackerTestHandler extends HandlerThread {
130
131         private DcTrackerTestHandler(String name) {
132             super(name);
133         }
134
135         @Override
136         public void onLooperPrepared() {
137             mDct = new DcTracker(mPhone);
138             setReady(true);
139         }
140     }
141
142     private class ApnSettingContentProvider extends MockContentProvider {
143
144         @Override
145         public Cursor query(Uri uri, String[] projection, String selection, String[] selectionArgs,
146                             String sortOrder) {
147             logd("ApnSettingContentProvider: query");
148             logd("   uri = " + uri);
149             logd("   projection = " + Arrays.toString(projection));
150             logd("   selection = " + selection);
151             logd("   selectionArgs = " + Arrays.toString(selectionArgs));
152             logd("   sortOrder = " + sortOrder);
153
154             if (uri.compareTo(Telephony.Carriers.CONTENT_URI) == 0) {
155                 if (projection == null && selectionArgs == null && selection != null) {
156
157                     Pattern pattern = Pattern.compile("^numeric = '([0-9]*)'");
158                     Matcher matcher = pattern.matcher(selection);
159                     if (!matcher.find()) {
160                         logd("Cannot find MCC/MNC from " + selection);
161                         return null;
162                     }
163
164                     String plmn = matcher.group(1);
165
166                     logd("Query '" + plmn + "' APN settings");
167                     MatrixCursor mc = new MatrixCursor(
168                             new String[]{Telephony.Carriers._ID, Telephony.Carriers.NUMERIC,
169                                     Telephony.Carriers.NAME, Telephony.Carriers.APN,
170                                     Telephony.Carriers.PROXY, Telephony.Carriers.PORT,
171                                     Telephony.Carriers.MMSC, Telephony.Carriers.MMSPROXY,
172                                     Telephony.Carriers.MMSPORT, Telephony.Carriers.USER,
173                                     Telephony.Carriers.PASSWORD, Telephony.Carriers.AUTH_TYPE,
174                                     Telephony.Carriers.TYPE,
175                                     Telephony.Carriers.PROTOCOL,
176                                     Telephony.Carriers.ROAMING_PROTOCOL,
177                                     Telephony.Carriers.CARRIER_ENABLED, Telephony.Carriers.BEARER,
178                                     Telephony.Carriers.BEARER_BITMASK,
179                                     Telephony.Carriers.PROFILE_ID,
180                                     Telephony.Carriers.MODEM_COGNITIVE,
181                                     Telephony.Carriers.MAX_CONNS, Telephony.Carriers.WAIT_TIME,
182                                     Telephony.Carriers.MAX_CONNS_TIME, Telephony.Carriers.MTU,
183                                     Telephony.Carriers.MVNO_TYPE,
184                                     Telephony.Carriers.MVNO_MATCH_DATA});
185
186                     mc.addRow(new Object[]{
187                             2163,                   // id
188                             plmn,                   // numeric
189                             "sp-mode",              // name
190                             FAKE_APN1,              // apn
191                             "",                     // proxy
192                             "",                     // port
193                             "",                     // mmsc
194                             "",                     // mmsproxy
195                             "",                     // mmsport
196                             "",                     // user
197                             "",                     // password
198                             -1,                     // authtype
199                             "default,supl",         // types
200                             "IP",                   // protocol
201                             "IP",                   // roaming_protocol
202                             1,                      // carrier_enabled
203                             0,                      // bearer
204                             0,                      // bearer_bitmask
205                             0,                      // profile_id
206                             0,                      // modem_cognitive
207                             0,                      // max_conns
208                             0,                      // wait_time
209                             0,                      // max_conns_time
210                             0,                      // mtu
211                             "",                     // mvno_type
212                             ""                      // mnvo_match_data
213                     });
214
215                     mc.addRow(new Object[]{
216                             2164,                   // id
217                             plmn,                   // numeric
218                             "mopera U",             // name
219                             FAKE_APN2,              // apn
220                             "",                     // proxy
221                             "",                     // port
222                             "",                     // mmsc
223                             "",                     // mmsproxy
224                             "",                     // mmsport
225                             "",                     // user
226                             "",                     // password
227                             -1,                     // authtype
228                             "default,supl",         // types
229                             "IP",                   // protocol
230                             "IP",                   // roaming_protocol
231                             1,                      // carrier_enabled
232                             0,                      // bearer
233                             0,                      // bearer_bitmask
234                             0,                      // profile_id
235                             0,                      // modem_cognitive
236                             0,                      // max_conns
237                             0,                      // wait_time
238                             0,                      // max_conns_time
239                             0,                      // mtu
240                             "",                     // mvno_type
241                             ""                      // mnvo_match_data
242                     });
243
244                     mc.addRow(new Object[]{
245                             2165,                   // id
246                             plmn,                   // numeric
247                             "b-mobile for Nexus",   // name
248                             FAKE_APN3,              // apn
249                             "",                     // proxy
250                             "",                     // port
251                             "",                     // mmsc
252                             "",                     // mmsproxy
253                             "",                     // mmsport
254                             "",                     // user
255                             "",                     // password
256                             -1,                     // authtype
257                             "ims",                  // types
258                             "IP",                   // protocol
259                             "IP",                   // roaming_protocol
260                             1,                      // carrier_enabled
261                             0,                      // bearer
262                             0,                      // bearer_bitmask
263                             0,                      // profile_id
264                             0,                      // modem_cognitive
265                             0,                      // max_conns
266                             0,                      // wait_time
267                             0,                      // max_conns_time
268                             0,                      // mtu
269                             "",                     // mvno_type
270                             ""                      // mnvo_match_data
271                     });
272
273                     return mc;
274                 }
275             }
276
277             return null;
278         }
279     }
280
281     @Before
282     public void setUp() throws Exception {
283         // set the lazy cp to the real content provider in order to use the real settings
284         ContentResolver realContentResolver = TestApplication.getAppContext().getContentResolver();
285         Settings.Global.getInt(realContentResolver, Settings.Global.MOBILE_DATA, 1);
286
287         logd("DcTrackerTest +Setup!");
288         super.setUp(getClass().getSimpleName());
289
290         doReturn("fake.action_detached").when(mPhone).getActionDetached();
291         doReturn("fake.action_attached").when(mPhone).getActionAttached();
292         doReturn("44010").when(mSimRecords).getOperatorNumeric();
293
294         mContextFixture.putStringArrayResource(com.android.internal.R.array.networkAttributes,
295                 sNetworkAttributes);
296         mContextFixture.putStringArrayResource(com.android.internal.R.array.
297                 config_mobile_tcp_buffers, new String[]{
298                 "umts:131072,262144,1452032,4096,16384,399360",
299                 "hspa:131072,262144,2441216,4096,16384,399360",
300                 "hsupa:131072,262144,2441216,4096,16384,399360",
301                 "hsdpa:131072,262144,2441216,4096,16384,399360",
302                 "hspap:131072,262144,2441216,4096,16384,399360",
303                 "edge:16384,32768,131072,4096,16384,65536",
304                 "gprs:4096,8192,24576,4096,8192,24576",
305                 "1xrtt:16384,32768,131070,4096,16384,102400",
306                 "evdo:131072,262144,1048576,4096,16384,524288",
307                 "lte:524288,1048576,8388608,262144,524288,4194304"});
308
309         ((MockContentResolver) mContext.getContentResolver()).addProvider(
310                 Telephony.Carriers.CONTENT_URI.getAuthority(), mApnSettingContentProvider);
311
312         doReturn(true).when(mSimRecords).getRecordsLoaded();
313         doReturn(PhoneConstants.State.IDLE).when(mCT).getState();
314         doReturn(true).when(mSST).getDesiredPowerState();
315         doReturn(true).when(mSST).getPowerStateFromCarrier();
316         doAnswer(
317                 new Answer<Void>() {
318                     @Override
319                     public Void answer(InvocationOnMock invocation) throws Throwable {
320                         mOnSubscriptionsChangedListener =
321                                 (SubscriptionManager.OnSubscriptionsChangedListener)
322                                         invocation.getArguments()[0];
323                         return null;
324                     }
325                 }
326         ).when(mSubscriptionManager).addOnSubscriptionsChangedListener(any());
327         doReturn(mSubscriptionInfo).when(mSubscriptionManager).getActiveSubscriptionInfo(anyInt());
328
329         doReturn(1).when(mIsub).getDefaultDataSubId();
330         doReturn(mIsub).when(mBinder).queryLocalInterface(anyString());
331         mServiceManagerMockedServices.put("isub", mBinder);
332
333         mContextFixture.putStringArrayResource(
334                 com.android.internal.R.array.config_cell_retries_per_error_code,
335                 new String[]{"36,2"});
336
337         mAlarmManager = (AlarmManager) mContext.getSystemService(Context.ALARM_SERVICE);
338         mBundle = mContextFixture.getCarrierConfigBundle();
339
340         mDcTrackerTestHandler = new DcTrackerTestHandler(getClass().getSimpleName());
341         mDcTrackerTestHandler.start();
342         waitUntilReady();
343         waitForMs(600);
344         logd("DcTrackerTest -Setup!");
345     }
346
347     @After
348     public void tearDown() throws Exception {
349         logd("DcTrackerTest -tearDown");
350         mDct.removeCallbacksAndMessages(null);
351         mDct = null;
352         mDcTrackerTestHandler.quitSafely();
353         super.tearDown();
354     }
355
356     // Create a successful data response
357     public static DataCallResponse createDataCallResponse() {
358
359         return new DataCallResponse(0, -1, 1, 2, "IP", FAKE_IFNAME,
360                 FAKE_ADDRESS, FAKE_DNS, FAKE_GATEWAY, FAKE_PCSCF_ADDRESS, 1440);
361     }
362
363     private void verifyDataProfile(DataProfile dp, String apn, int profileId,
364                                    int supportedApnTypesBitmap) {
365         assertEquals(profileId, dp.profileId);
366         assertEquals(apn, dp.apn);
367         assertEquals("IP", dp.protocol);
368         assertEquals(0, dp.authType);
369         assertEquals("", dp.user);
370         assertEquals("", dp.password);
371         assertEquals(0, dp.type);
372         assertEquals(0, dp.maxConnsTime);
373         assertEquals(0, dp.maxConns);
374         assertEquals(0, dp.waitTime);
375         assertTrue(dp.enabled);
376         assertEquals(supportedApnTypesBitmap, dp.supportedApnTypesBitmap);
377         assertEquals("IP", dp.roamingProtocol);
378         assertEquals(0, dp.bearerBitmap);
379         assertEquals(0, dp.mtu);
380         assertEquals("", dp.mvnoType);
381         assertEquals("", dp.mvnoMatchData);
382         assertFalse(dp.modemCognitive);
383     }
384
385     private void verifyDataConnected(final String apnSetting) {
386         verify(mPhone, times(1)).notifyDataConnection(eq(Phone.REASON_CONNECTED),
387                 eq(PhoneConstants.APN_TYPE_DEFAULT));
388
389         verify(mAlarmManager, times(1)).set(eq(AlarmManager.ELAPSED_REALTIME_WAKEUP), anyLong(),
390                 any(PendingIntent.class));
391
392         assertEquals(apnSetting, mDct.getActiveApnString(PhoneConstants.APN_TYPE_DEFAULT));
393         assertArrayEquals(new String[]{PhoneConstants.APN_TYPE_DEFAULT}, mDct.getActiveApnTypes());
394         assertTrue(mDct.getAnyDataEnabled());
395
396         assertEquals(DctConstants.State.CONNECTED, mDct.getOverallState());
397         assertEquals(DctConstants.State.CONNECTED, mDct.getState(PhoneConstants.APN_TYPE_DEFAULT));
398
399         LinkProperties linkProperties = mDct.getLinkProperties(PhoneConstants.APN_TYPE_DEFAULT);
400         assertEquals(FAKE_IFNAME, linkProperties.getInterfaceName());
401         assertEquals(1, linkProperties.getAddresses().size());
402         assertEquals(FAKE_ADDRESS, linkProperties.getAddresses().get(0).getHostAddress());
403         assertEquals(1, linkProperties.getDnsServers().size());
404         assertEquals(FAKE_DNS, linkProperties.getDnsServers().get(0).getHostAddress());
405         assertEquals(FAKE_GATEWAY, linkProperties.getRoutes().get(0).getGateway().getHostAddress());
406     }
407
408     private boolean isDataAllowed(DataAllowFailReason dataAllowFailReasons) {
409         try {
410             Method method = DcTracker.class.getDeclaredMethod("isDataAllowed",
411                     DataAllowFailReason.class);
412             method.setAccessible(true);
413             return (boolean) method.invoke(mDct, dataAllowFailReasons);
414         } catch (Exception e) {
415             fail(e.toString());
416             return false;
417         }
418     }
419
420     // Test the normal data call setup scenario.
421     @Test
422     @MediumTest
423     public void testDataSetup() {
424
425         mDct.setDataEnabled(true);
426
427         mSimulatedCommands.setDataCallResponse(true, createDataCallResponse());
428
429         DataAllowFailReason failureReason = new DataAllowFailReason();
430         boolean allowed = isDataAllowed(failureReason);
431         assertFalse(failureReason.getDataAllowFailReason(), allowed);
432
433         logd("Sending EVENT_RECORDS_LOADED");
434         mDct.sendMessage(mDct.obtainMessage(DctConstants.EVENT_RECORDS_LOADED, null));
435         waitForMs(200);
436
437         ArgumentCaptor<String> apnTypeArgumentCaptor = ArgumentCaptor.forClass(String.class);
438         verify(mPhone, times(sNetworkAttributes.length)).notifyDataConnection(
439                 eq(Phone.REASON_SIM_LOADED), apnTypeArgumentCaptor.capture(),
440                 eq(PhoneConstants.DataState.DISCONNECTED));
441
442         assertEquals(sApnTypes, apnTypeArgumentCaptor.getAllValues());
443
444         logd("Sending EVENT_DATA_CONNECTION_ATTACHED");
445         mDct.sendMessage(mDct.obtainMessage(DctConstants.EVENT_DATA_CONNECTION_ATTACHED, null));
446         waitForMs(200);
447
448         apnTypeArgumentCaptor = ArgumentCaptor.forClass(String.class);
449         verify(mPhone, times(sNetworkAttributes.length)).notifyDataConnection(
450                 eq(Phone.REASON_DATA_ATTACHED), apnTypeArgumentCaptor.capture(),
451                 eq(PhoneConstants.DataState.DISCONNECTED));
452
453         assertEquals(sApnTypes, apnTypeArgumentCaptor.getAllValues());
454
455         apnTypeArgumentCaptor = ArgumentCaptor.forClass(String.class);
456         verify(mPhone, times(sNetworkAttributes.length)).notifyDataConnection(
457                 eq(Phone.REASON_DATA_ENABLED), apnTypeArgumentCaptor.capture(),
458                 eq(PhoneConstants.DataState.DISCONNECTED));
459
460         assertEquals(sApnTypes, apnTypeArgumentCaptor.getAllValues());
461
462         logd("Sending EVENT_ENABLE_NEW_APN");
463         // APN id 0 is APN_TYPE_DEFAULT
464         mDct.setEnabled(0, true);
465         waitForMs(200);
466
467         failureReason.clearAllReasons();
468         allowed = isDataAllowed(failureReason);
469         assertTrue(failureReason.getDataAllowFailReason(), allowed);
470
471         ArgumentCaptor<DataProfile> dpCaptor = ArgumentCaptor.forClass(DataProfile.class);
472         // Verify if RIL command was sent properly.
473         verify(mSimulatedCommandsVerifier, times(1)).setupDataCall(
474                 eq(ServiceState.RIL_RADIO_TECHNOLOGY_UMTS), dpCaptor.capture(),
475                 eq(false), eq(false), any(Message.class));
476         verifyDataProfile(dpCaptor.getValue(), FAKE_APN1, 0, 5);
477
478         verifyDataConnected(FAKE_APN1);
479     }
480
481     // Test the scenario where the first data call setup is failed, and then retry the setup later.
482     @Test
483     @MediumTest
484     public void testDataRetry() {
485
486         mDct.setDataEnabled(true);
487
488         // LOST_CONNECTION(0x10004) is a non-permanent failure, so we'll retry data setup later.
489         DataCallResponse dcResponse = new DataCallResponse(0x10004, -1, 1, 2, "IP", FAKE_IFNAME,
490                 FAKE_ADDRESS, FAKE_DNS, FAKE_GATEWAY, FAKE_PCSCF_ADDRESS, 1440);
491         // Simulate RIL fails the data call setup
492         mSimulatedCommands.setDataCallResponse(false, dcResponse);
493
494         DataAllowFailReason failureReason = new DataAllowFailReason();
495         boolean allowed = isDataAllowed(failureReason);
496         assertFalse(failureReason.getDataAllowFailReason(), allowed);
497
498         logd("Sending EVENT_RECORDS_LOADED");
499         mDct.sendMessage(mDct.obtainMessage(DctConstants.EVENT_RECORDS_LOADED, null));
500         waitForMs(200);
501
502         ArgumentCaptor<String> apnTypeArgumentCaptor = ArgumentCaptor.forClass(String.class);
503         verify(mPhone, times(sNetworkAttributes.length)).notifyDataConnection(
504                 eq(Phone.REASON_SIM_LOADED), apnTypeArgumentCaptor.capture(),
505                 eq(PhoneConstants.DataState.DISCONNECTED));
506
507         assertEquals(sApnTypes, apnTypeArgumentCaptor.getAllValues());
508
509         logd("Sending EVENT_DATA_CONNECTION_ATTACHED");
510         mDct.sendMessage(mDct.obtainMessage(DctConstants.EVENT_DATA_CONNECTION_ATTACHED, null));
511         waitForMs(200);
512
513         apnTypeArgumentCaptor = ArgumentCaptor.forClass(String.class);
514         verify(mPhone, times(sNetworkAttributes.length)).notifyDataConnection(
515                 eq(Phone.REASON_DATA_ATTACHED), apnTypeArgumentCaptor.capture(),
516                 eq(PhoneConstants.DataState.DISCONNECTED));
517
518         assertEquals(sApnTypes, apnTypeArgumentCaptor.getAllValues());
519
520         apnTypeArgumentCaptor = ArgumentCaptor.forClass(String.class);
521         verify(mPhone, times(sNetworkAttributes.length)).notifyDataConnection(
522                 eq(Phone.REASON_DATA_ENABLED), apnTypeArgumentCaptor.capture(),
523                 eq(PhoneConstants.DataState.DISCONNECTED));
524
525         assertEquals(sApnTypes, apnTypeArgumentCaptor.getAllValues());
526
527         logd("Sending EVENT_ENABLE_NEW_APN");
528         // APN id 0 is APN_TYPE_DEFAULT
529         mDct.setEnabled(0, true);
530         waitForMs(200);
531
532
533         failureReason.clearAllReasons();
534         allowed = isDataAllowed(failureReason);
535         assertTrue(failureReason.getDataAllowFailReason(), allowed);
536
537         ArgumentCaptor<DataProfile> dpCaptor = ArgumentCaptor.forClass(DataProfile.class);
538         // Verify if RIL command was sent properly.
539         verify(mSimulatedCommandsVerifier, times(1)).setupDataCall(
540                 eq(ServiceState.RIL_RADIO_TECHNOLOGY_UMTS), dpCaptor.capture(),
541                 eq(false), eq(false), any(Message.class));
542         verifyDataProfile(dpCaptor.getValue(), FAKE_APN1, 0, 5);
543
544         // Make sure we never notify connected because the data call setup is supposed to fail.
545         verify(mPhone, never()).notifyDataConnection(eq(Phone.REASON_CONNECTED),
546                 eq(PhoneConstants.APN_TYPE_DEFAULT));
547
548         // Verify the retry manger schedule another data call setup.
549         verify(mAlarmManager, times(1)).setExact(eq(AlarmManager.ELAPSED_REALTIME_WAKEUP),
550                 anyLong(), any(PendingIntent.class));
551
552         // This time we'll let RIL command succeed.
553         mSimulatedCommands.setDataCallResponse(true, createDataCallResponse());
554
555         // Simulate the timer expires.
556         Intent intent = new Intent("com.android.internal.telephony.data-reconnect.default");
557         intent.putExtra("reconnect_alarm_extra_type", PhoneConstants.APN_TYPE_DEFAULT);
558         intent.putExtra(PhoneConstants.SUBSCRIPTION_KEY, 0);
559         intent.addFlags(Intent.FLAG_RECEIVER_FOREGROUND);
560         mContext.sendBroadcast(intent);
561         waitForMs(200);
562
563         dpCaptor = ArgumentCaptor.forClass(DataProfile.class);
564         // Verify if RIL command was sent properly.
565         verify(mSimulatedCommandsVerifier, times(2)).setupDataCall(
566                 eq(ServiceState.RIL_RADIO_TECHNOLOGY_UMTS), dpCaptor.capture(),
567                 eq(false), eq(false), any(Message.class));
568         verifyDataProfile(dpCaptor.getValue(), FAKE_APN2, 0, 5);
569
570         // Verify connected with APN2 setting.
571         verifyDataConnected(FAKE_APN2);
572     }
573
574     @Test
575     @MediumTest
576     public void testUserDisableData() throws Exception {
577         //step 1: setup two DataCalls one for Metered: default, another one for Non-metered: IMS
578         //set Default and MMS to be metered in the CarrierConfigManager
579         boolean dataEnabled = mDct.getDataEnabled();
580         mBundle.putStringArray(CarrierConfigManager.KEY_CARRIER_METERED_APN_TYPES_STRINGS,
581                 new String[]{PhoneConstants.APN_TYPE_DEFAULT, PhoneConstants.APN_TYPE_MMS});
582         mDct.setEnabled(5, true);
583         mDct.setEnabled(0, true);
584
585         logd("Sending EVENT_RECORDS_LOADED");
586         mDct.sendMessage(mDct.obtainMessage(DctConstants.EVENT_RECORDS_LOADED, null));
587         waitForMs(200);
588
589         logd("Sending EVENT_DATA_CONNECTION_ATTACHED");
590         mDct.sendMessage(mDct.obtainMessage(DctConstants.EVENT_DATA_CONNECTION_ATTACHED, null));
591         waitForMs(200);
592
593         logd("Sending DATA_ENABLED_CMD");
594         mDct.setDataEnabled(true);
595
596         waitForMs(200);
597         ArgumentCaptor<DataProfile> dpCaptor = ArgumentCaptor.forClass(DataProfile.class);
598         verify(mSimulatedCommandsVerifier, times(2)).setupDataCall(
599                 eq(ServiceState.RIL_RADIO_TECHNOLOGY_UMTS), dpCaptor.capture(),
600                 eq(false), eq(false), any(Message.class));
601         verifyDataProfile(dpCaptor.getValue(), FAKE_APN1, 0, 5);
602
603         logd("Sending DATA_DISABLED_CMD");
604         mDct.setDataEnabled(false);
605         waitForMs(200);
606
607         // expected tear down all metered DataConnections
608         verify(mSimulatedCommandsVerifier, times(1)).deactivateDataCall(anyInt(), anyInt(),
609                 any(Message.class));
610         assertEquals(DctConstants.State.CONNECTED, mDct.getOverallState());
611         assertEquals(DctConstants.State.IDLE, mDct.getState(PhoneConstants.APN_TYPE_DEFAULT));
612         assertEquals(DctConstants.State.CONNECTED, mDct.getState(PhoneConstants.APN_TYPE_IMS));
613
614         // reset the setting at the end of this test
615         mDct.setDataEnabled(dataEnabled);
616         waitForMs(200);
617     }
618
619     @Test
620     @MediumTest
621     public void testUserDisableRoaming() throws Exception {
622         //step 1: setup two DataCalls one for Metered: default, another one for Non-metered: IMS
623         //step 2: set roaming disabled, data is enabled
624         //step 3: under roaming service
625         //step 4: only tear down metered data connections.
626
627         //set Default and MMS to be metered in the CarrierConfigManager
628         boolean roamingEnabled = mDct.getDataOnRoamingEnabled();
629         boolean dataEnabled = mDct.getDataEnabled();
630
631         mBundle.putStringArray(CarrierConfigManager.KEY_CARRIER_METERED_ROAMING_APN_TYPES_STRINGS,
632                 new String[]{PhoneConstants.APN_TYPE_DEFAULT, PhoneConstants.APN_TYPE_MMS});
633         mDct.setEnabled(5, true);
634         mDct.setEnabled(0, true);
635
636         logd("Sending EVENT_RECORDS_LOADED");
637         mDct.sendMessage(mDct.obtainMessage(DctConstants.EVENT_RECORDS_LOADED, null));
638         waitForMs(200);
639
640         logd("Sending EVENT_DATA_CONNECTION_ATTACHED");
641         mDct.sendMessage(mDct.obtainMessage(DctConstants.EVENT_DATA_CONNECTION_ATTACHED, null));
642         waitForMs(200);
643
644         logd("Sending DATA_ENABLED_CMD");
645         mDct.setDataEnabled(true);
646
647         waitForMs(300);
648         ArgumentCaptor<DataProfile> dpCaptor = ArgumentCaptor.forClass(DataProfile.class);
649         verify(mSimulatedCommandsVerifier, times(2)).setupDataCall(
650                 eq(ServiceState.RIL_RADIO_TECHNOLOGY_UMTS), dpCaptor.capture(),
651                 eq(false), eq(false), any(Message.class));
652         verifyDataProfile(dpCaptor.getValue(), FAKE_APN1, 0, 5);
653
654         //user is in roaming
655         doReturn(true).when(mServiceState).getDataRoaming();
656         logd("Sending DISABLE_ROAMING_CMD");
657         mDct.setDataOnRoamingEnabled(false);
658         mDct.sendMessage(mDct.obtainMessage(DctConstants.EVENT_ROAMING_ON));
659         waitForMs(200);
660
661         // expected tear down all metered DataConnections
662         verify(mSimulatedCommandsVerifier, times(1)).deactivateDataCall(anyInt(), anyInt(),
663                 any(Message.class));
664         assertEquals(DctConstants.State.CONNECTED, mDct.getOverallState());
665         assertEquals(DctConstants.State.IDLE, mDct.getState(PhoneConstants.APN_TYPE_DEFAULT));
666         assertEquals(DctConstants.State.CONNECTED, mDct.getState(PhoneConstants.APN_TYPE_IMS));
667
668         // reset roaming settings / data enabled settings at end of this test
669         mDct.setDataOnRoamingEnabled(roamingEnabled);
670         mDct.setDataEnabled(dataEnabled);
671         waitForMs(200);
672     }
673
674     @FlakyTest
675     @Test
676     @MediumTest
677     public void testDataCallOnUserDisableRoaming() throws Exception {
678         //step 1: mock under roaming service and user disabled roaming from settings.
679         //step 2: user toggled data settings on
680         //step 3: only non-metered data call is established
681
682         boolean roamingEnabled = mDct.getDataOnRoamingEnabled();
683         boolean dataEnabled = mDct.getDataEnabled();
684
685         //set Default and MMS to be metered in the CarrierConfigManager
686         mBundle.putStringArray(CarrierConfigManager.KEY_CARRIER_METERED_ROAMING_APN_TYPES_STRINGS,
687                 new String[]{PhoneConstants.APN_TYPE_DEFAULT, PhoneConstants.APN_TYPE_MMS});
688         mDct.setEnabled(5, true);
689         mDct.setEnabled(0, true);
690         doReturn(true).when(mServiceState).getDataRoaming();
691
692         logd("Sending DISABLE_ROAMING_CMD");
693         mDct.setDataOnRoamingEnabled(false);
694
695         logd("Sending EVENT_RECORDS_LOADED");
696         mDct.sendMessage(mDct.obtainMessage(DctConstants.EVENT_RECORDS_LOADED, null));
697         waitForMs(200);
698
699         logd("Sending EVENT_DATA_CONNECTION_ATTACHED");
700         mDct.sendMessage(mDct.obtainMessage(DctConstants.EVENT_DATA_CONNECTION_ATTACHED, null));
701         waitForMs(200);
702
703         logd("Sending DATA_ENABLED_CMD");
704         mDct.setDataEnabled(true);
705
706         waitForMs(200);
707         ArgumentCaptor<DataProfile> dpCaptor = ArgumentCaptor.forClass(DataProfile.class);
708         verify(mSimulatedCommandsVerifier, times(1)).setupDataCall(
709                 eq(ServiceState.RIL_RADIO_TECHNOLOGY_UMTS), dpCaptor.capture(),
710                 eq(false), eq(false), any(Message.class));
711         verifyDataProfile(dpCaptor.getValue(), FAKE_APN3, 2, 64);
712
713         assertEquals(DctConstants.State.CONNECTED, mDct.getOverallState());
714         assertEquals(DctConstants.State.IDLE, mDct.getState(PhoneConstants.APN_TYPE_DEFAULT));
715         assertEquals(DctConstants.State.CONNECTED, mDct.getState(PhoneConstants.APN_TYPE_IMS));
716
717         // reset roaming settings / data enabled settings at end of this test
718         mDct.setDataOnRoamingEnabled(roamingEnabled);
719         mDct.setDataEnabled(dataEnabled);
720         waitForMs(200);
721     }
722
723     // Test the default data switch scenario.
724     @Test
725     @MediumTest
726     public void testDDSResetAutoAttach() throws Exception {
727
728         mDct.setDataEnabled(true);
729
730         mContextFixture.putBooleanResource(
731                 com.android.internal.R.bool.config_auto_attach_data_on_creation, true);
732
733         mSimulatedCommands.setDataCallResponse(true, createDataCallResponse());
734
735         DataAllowFailReason failureReason = new DataAllowFailReason();
736         boolean allowed = isDataAllowed(failureReason);
737         assertFalse(failureReason.getDataAllowFailReason(), allowed);
738
739         ArgumentCaptor<Integer> intArgumentCaptor = ArgumentCaptor.forClass(Integer.class);
740         verify(mUiccController, times(1)).registerForIccChanged(eq(mDct),
741                 intArgumentCaptor.capture(), eq(null));
742         // Ideally this should send EVENT_ICC_CHANGED.
743         mDct.sendMessage(mDct.obtainMessage(intArgumentCaptor.getValue(), null));
744         waitForMs(100);
745
746         verify(mSimRecords, times(1)).registerForRecordsLoaded(eq(mDct),
747                 intArgumentCaptor.capture(), eq(null));
748         // Ideally this should send EVENT_RECORDS_LOADED.
749         mDct.sendMessage(mDct.obtainMessage(intArgumentCaptor.getValue(), null));
750         waitForMs(100);
751
752         verify(mSST, times(1)).registerForDataConnectionAttached(eq(mDct),
753                 intArgumentCaptor.capture(), eq(null));
754         // Ideally this should send EVENT_DATA_CONNECTION_ATTACHED");
755         mDct.sendMessage(mDct.obtainMessage(intArgumentCaptor.getValue(), null));
756         waitForMs(200);
757
758         NetworkRequest nr = new NetworkRequest.Builder()
759                 .addCapability(NetworkCapabilities.NET_CAPABILITY_INTERNET).build();
760         LocalLog l = new LocalLog(100);
761         mDct.requestNetwork(nr, l);
762         waitForMs(200);
763
764         verifyDataConnected(FAKE_APN1);
765
766         assertTrue(mDct.getAutoAttachOnCreation());
767         mDct.update();
768         // The auto attach flag should be reset after update
769         assertFalse(mDct.getAutoAttachOnCreation());
770
771         verify(mSST, times(1)).registerForDataConnectionDetached(eq(mDct),
772                 intArgumentCaptor.capture(), eq(null));
773         // Ideally this should send EVENT_DATA_CONNECTION_DETACHED
774         mDct.sendMessage(mDct.obtainMessage(intArgumentCaptor.getValue(), null));
775         waitForMs(200);
776
777         // Data should not be allowed since auto attach flag has been reset.
778         failureReason.clearAllReasons();
779         allowed = isDataAllowed(failureReason);
780         assertFalse(failureReason.getDataAllowFailReason(), allowed);
781     }
782
783     // Test for API carrierActionSetMeteredApnsEnabled.
784     @FlakyTest
785     @Test
786     @MediumTest
787     public void testCarrierActionSetMeteredApnsEnabled() throws Exception {
788         //step 1: setup two DataCalls one for Internet and IMS
789         //step 2: set data is enabled
790         //step 3: cold sim is detected
791         //step 4: all data connection is torn down
792         mBundle.putStringArray(CarrierConfigManager.KEY_CARRIER_METERED_APN_TYPES_STRINGS,
793                 new String[]{PhoneConstants.APN_TYPE_DEFAULT, PhoneConstants.APN_TYPE_MMS});
794
795         boolean dataEnabled = mDct.getDataEnabled();
796         mDct.setDataEnabled(true);
797
798         mDct.setEnabled(5, true);
799         mDct.setEnabled(0, true);
800
801         logd("Sending EVENT_RECORDS_LOADED");
802         mDct.sendMessage(mDct.obtainMessage(DctConstants.EVENT_RECORDS_LOADED, null));
803         waitForMs(200);
804
805         logd("Sending EVENT_DATA_CONNECTION_ATTACHED");
806         mDct.sendMessage(mDct.obtainMessage(DctConstants.EVENT_DATA_CONNECTION_ATTACHED, null));
807         waitForMs(200);
808
809         ArgumentCaptor<DataProfile> dpCaptor = ArgumentCaptor.forClass(DataProfile.class);
810         verify(mSimulatedCommandsVerifier, times(2)).setupDataCall(
811                 eq(ServiceState.RIL_RADIO_TECHNOLOGY_UMTS), dpCaptor.capture(),
812                 eq(false), eq(false), any(Message.class));
813         verifyDataProfile(dpCaptor.getValue(), FAKE_APN1, 0, 5);
814         assertEquals(DctConstants.State.CONNECTED, mDct.getOverallState());
815
816         Message msg = mDct.obtainMessage(DctConstants.EVENT_SET_CARRIER_DATA_ENABLED);
817         AsyncResult.forMessage(msg).result = false;
818         mDct.sendMessage(msg);
819
820         waitForMs(100);
821
822         // Validate all metered data connections have been torn down
823         verify(mSimulatedCommandsVerifier, times(1)).deactivateDataCall(anyInt(), anyInt(),
824                 any(Message.class));
825         assertEquals(DctConstants.State.CONNECTED, mDct.getOverallState());
826         assertEquals(DctConstants.State.IDLE, mDct.getState(PhoneConstants.APN_TYPE_DEFAULT));
827
828         // Reset settings at the end of test
829         mDct.setDataEnabled(dataEnabled);
830         waitForMs(200);
831     }
832 }