Home | History | Annotate | Download | only in policy
      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 com.android.systemui.statusbar.policy;
     18 
     19 import android.content.Intent;
     20 import android.net.ConnectivityManager;
     21 import android.net.NetworkCapabilities;
     22 import android.net.wifi.WifiManager;
     23 import android.os.Looper;
     24 import android.provider.Settings;
     25 import android.provider.Settings.Global;
     26 import android.telephony.PhoneStateListener;
     27 import android.telephony.ServiceState;
     28 import android.telephony.SignalStrength;
     29 import android.telephony.SubscriptionInfo;
     30 import android.telephony.SubscriptionManager;
     31 import android.telephony.TelephonyManager;
     32 import android.util.Log;
     33 import com.android.internal.telephony.cdma.EriInfo;
     34 import com.android.settingslib.net.DataUsageController;
     35 import com.android.systemui.statusbar.phone.SignalDrawable;
     36 import com.android.systemui.statusbar.policy.DeviceProvisionedController.DeviceProvisionedListener;
     37 import com.android.systemui.statusbar.policy.NetworkController.IconState;
     38 import com.android.systemui.statusbar.policy.NetworkController.SignalCallback;
     39 import com.android.systemui.statusbar.policy.NetworkControllerImpl.Config;
     40 import com.android.systemui.statusbar.policy.NetworkControllerImpl.SubscriptionDefaults;
     41 import com.android.systemui.SysuiTestCase;
     42 
     43 import org.junit.Before;
     44 import org.junit.Rule;
     45 import org.junit.rules.TestWatcher;
     46 import org.junit.runner.Description;
     47 import org.mockito.ArgumentCaptor;
     48 import org.mockito.Mockito;
     49 
     50 import java.io.PrintWriter;
     51 import java.io.StringWriter;
     52 import java.util.ArrayList;
     53 import java.util.List;
     54 
     55 import static junit.framework.Assert.assertEquals;
     56 
     57 import static org.mockito.Matchers.any;
     58 import static org.mockito.Matchers.anyBoolean;
     59 import static org.mockito.Matchers.anyInt;
     60 import static org.mockito.Matchers.anyString;
     61 import static org.mockito.Matchers.eq;
     62 import static org.mockito.Mockito.doAnswer;
     63 import static org.mockito.Mockito.mock;
     64 import static org.mockito.Mockito.when;
     65 
     66 public class NetworkControllerBaseTest extends SysuiTestCase {
     67     private static final String TAG = "NetworkControllerBaseTest";
     68     protected static final int DEFAULT_LEVEL = 2;
     69     protected static final int DEFAULT_SIGNAL_STRENGTH = DEFAULT_LEVEL;
     70     protected static final int DEFAULT_QS_SIGNAL_STRENGTH = DEFAULT_LEVEL;
     71     protected static final int DEFAULT_ICON = TelephonyIcons.ICON_3G;
     72     protected static final int DEFAULT_QS_ICON = TelephonyIcons.QS_DATA_3G;
     73 
     74     protected NetworkControllerImpl mNetworkController;
     75     protected MobileSignalController mMobileSignalController;
     76     protected PhoneStateListener mPhoneStateListener;
     77     protected SignalStrength mSignalStrength;
     78     protected ServiceState mServiceState;
     79     protected ConnectivityManager mMockCm;
     80     protected WifiManager mMockWm;
     81     protected SubscriptionManager mMockSm;
     82     protected TelephonyManager mMockTm;
     83     protected Config mConfig;
     84     protected CallbackHandler mCallbackHandler;
     85     protected SubscriptionDefaults mMockSubDefaults;
     86     protected DeviceProvisionedController mMockProvisionController;
     87     protected DeviceProvisionedListener mUserCallback;
     88 
     89     protected int mSubId;
     90 
     91     private NetworkCapabilities mNetCapabilities;
     92 
     93     @Rule
     94     public TestWatcher failWatcher = new TestWatcher() {
     95         @Override
     96         protected void failed(Throwable e, Description description) {
     97             // Print out mNetworkController state if the test fails.
     98             StringWriter sw = new StringWriter();
     99             PrintWriter pw = new PrintWriter(sw);
    100             mNetworkController.dump(null, pw, null);
    101             pw.flush();
    102             Log.d(TAG, sw.toString());
    103         }
    104     };
    105 
    106     @Before
    107     public void setUp() throws Exception {
    108         Settings.Global.putInt(mContext.getContentResolver(), Global.AIRPLANE_MODE_ON, 0);
    109         mMockWm = mock(WifiManager.class);
    110         mMockTm = mock(TelephonyManager.class);
    111         mMockSm = mock(SubscriptionManager.class);
    112         mMockCm = mock(ConnectivityManager.class);
    113         mMockSubDefaults = mock(SubscriptionDefaults.class);
    114         mNetCapabilities = new NetworkCapabilities();
    115         when(mMockCm.isNetworkSupported(ConnectivityManager.TYPE_MOBILE)).thenReturn(true);
    116         when(mMockCm.getDefaultNetworkCapabilitiesForUser(0)).thenReturn(
    117                 new NetworkCapabilities[] { mNetCapabilities });
    118 
    119         mSignalStrength = mock(SignalStrength.class);
    120         mServiceState = mock(ServiceState.class);
    121 
    122         mConfig = new Config();
    123         mConfig.hspaDataDistinguishable = true;
    124         mCallbackHandler = mock(CallbackHandler.class);
    125 
    126         mMockProvisionController = mock(DeviceProvisionedController.class);
    127         when(mMockProvisionController.isUserSetup(anyInt())).thenReturn(true);
    128         doAnswer(invocation -> {
    129             mUserCallback = (DeviceProvisionedListener) invocation.getArguments()[0];
    130             mUserCallback.onUserSetupChanged();
    131             mUserCallback.onDeviceProvisionedChanged();
    132             return null;
    133         }).when(mMockProvisionController).addCallback(any());
    134 
    135         mNetworkController = new NetworkControllerImpl(mContext, mMockCm, mMockTm, mMockWm, mMockSm,
    136                 mConfig, Looper.getMainLooper(), mCallbackHandler,
    137                 mock(AccessPointControllerImpl.class), mock(DataUsageController.class),
    138                 mMockSubDefaults, mMockProvisionController);
    139         setupNetworkController();
    140 
    141         // Trigger blank callbacks to always get the current state (some tests don't trigger
    142         // changes from default state).
    143         mNetworkController.addCallback(mock(SignalCallback.class));
    144         mNetworkController.addEmergencyListener(null);
    145     }
    146 
    147     protected void setupNetworkController() {
    148         // For now just pretend to be the data sim, so we can test that too.
    149         mSubId = SubscriptionManager.DEFAULT_SUBSCRIPTION_ID;
    150         when(mMockTm.getDataEnabled(mSubId)).thenReturn(true);
    151         setDefaultSubId(mSubId);
    152         setSubscriptions(mSubId);
    153         mMobileSignalController = mNetworkController.mMobileSignalControllers.get(mSubId);
    154         mPhoneStateListener = mMobileSignalController.mPhoneStateListener;
    155     }
    156 
    157     protected void setDefaultSubId(int subId) {
    158         when(mMockSubDefaults.getDefaultDataSubId()).thenReturn(subId);
    159         when(mMockSubDefaults.getDefaultVoiceSubId()).thenReturn(subId);
    160     }
    161 
    162     protected void setSubscriptions(int... subIds) {
    163         List<SubscriptionInfo> subs = new ArrayList<SubscriptionInfo>();
    164         for (int subId : subIds) {
    165             SubscriptionInfo subscription = mock(SubscriptionInfo.class);
    166             when(subscription.getSubscriptionId()).thenReturn(subId);
    167             subs.add(subscription);
    168         }
    169         when(mMockSm.getActiveSubscriptionInfoList()).thenReturn(subs);
    170         mNetworkController.doUpdateMobileControllers();
    171     }
    172 
    173     protected NetworkControllerImpl setUpNoMobileData() {
    174       when(mMockCm.isNetworkSupported(ConnectivityManager.TYPE_MOBILE)).thenReturn(false);
    175       NetworkControllerImpl networkControllerNoMobile
    176               = new NetworkControllerImpl(mContext, mMockCm, mMockTm, mMockWm, mMockSm,
    177                         mConfig, mContext.getMainLooper(), mCallbackHandler,
    178                         mock(AccessPointControllerImpl.class),
    179                         mock(DataUsageController.class), mMockSubDefaults,
    180                         mock(DeviceProvisionedController.class));
    181 
    182       setupNetworkController();
    183 
    184       return networkControllerNoMobile;
    185 
    186     }
    187 
    188     // 2 Bars 3G GSM.
    189     public void setupDefaultSignal() {
    190         setIsGsm(true);
    191         setVoiceRegState(ServiceState.STATE_IN_SERVICE);
    192         setGsmRoaming(false);
    193         setLevel(DEFAULT_LEVEL);
    194         updateDataConnectionState(TelephonyManager.DATA_CONNECTED,
    195                 TelephonyManager.NETWORK_TYPE_UMTS);
    196         setConnectivity(NetworkCapabilities.TRANSPORT_CELLULAR, true, true);
    197     }
    198 
    199     public void setConnectivity(int networkType, boolean inetCondition, boolean isConnected) {
    200         Intent i = new Intent(ConnectivityManager.INET_CONDITION_ACTION);
    201         // TODO: Separate out into several NetworkCapabilities.
    202         if (isConnected) {
    203             mNetCapabilities.addTransportType(networkType);
    204         } else {
    205             mNetCapabilities.removeTransportType(networkType);
    206         }
    207         if (inetCondition) {
    208             mNetCapabilities.addCapability(NetworkCapabilities.NET_CAPABILITY_VALIDATED);
    209         } else {
    210             mNetCapabilities.removeCapability(NetworkCapabilities.NET_CAPABILITY_VALIDATED);
    211         }
    212 
    213         mNetworkController.onReceive(mContext, i);
    214     }
    215 
    216     public void setGsmRoaming(boolean isRoaming) {
    217         when(mServiceState.getRoaming()).thenReturn(isRoaming);
    218         updateServiceState();
    219     }
    220 
    221     public void setCdmaRoaming(boolean isRoaming) {
    222         when(mServiceState.getCdmaEriIconIndex()).thenReturn(isRoaming ?
    223                 EriInfo.ROAMING_INDICATOR_ON : EriInfo.ROAMING_INDICATOR_OFF);
    224         when(mServiceState.getCdmaEriIconMode()).thenReturn(isRoaming ?
    225                 EriInfo.ROAMING_ICON_MODE_NORMAL : -1);
    226         updateServiceState();
    227     }
    228 
    229     public void setVoiceRegState(int voiceRegState) {
    230         when(mServiceState.getVoiceRegState()).thenReturn(voiceRegState);
    231         updateServiceState();
    232     }
    233 
    234     public void setDataRegState(int dataRegState) {
    235         when(mServiceState.getDataRegState()).thenReturn(dataRegState);
    236         updateServiceState();
    237     }
    238 
    239     public void setIsEmergencyOnly(boolean isEmergency) {
    240         when(mServiceState.isEmergencyOnly()).thenReturn(isEmergency);
    241         updateServiceState();
    242     }
    243 
    244     public void setCdmaLevel(int level) {
    245         when(mSignalStrength.getCdmaLevel()).thenReturn(level);
    246         updateSignalStrength();
    247     }
    248 
    249     public void setLevel(int level) {
    250         when(mSignalStrength.getLevel()).thenReturn(level);
    251         updateSignalStrength();
    252     }
    253 
    254     public void setIsGsm(boolean gsm) {
    255         when(mSignalStrength.isGsm()).thenReturn(gsm);
    256         updateSignalStrength();
    257     }
    258 
    259     public void setCdmaEri(int index, int mode) {
    260         // TODO: Figure this out.
    261     }
    262 
    263     private void updateSignalStrength() {
    264         Log.d(TAG, "Sending Signal Strength: " + mSignalStrength);
    265         mPhoneStateListener.onSignalStrengthsChanged(mSignalStrength);
    266     }
    267 
    268     protected void updateServiceState() {
    269         Log.d(TAG, "Sending Service State: " + mServiceState);
    270         mPhoneStateListener.onServiceStateChanged(mServiceState);
    271     }
    272 
    273     public void updateCallState(int state) {
    274         // Inputs not currently used in NetworkControllerImpl.
    275         mPhoneStateListener.onCallStateChanged(state, "0123456789");
    276     }
    277 
    278     public void updateDataConnectionState(int dataState, int dataNetType) {
    279         when(mServiceState.getDataNetworkType()).thenReturn(dataNetType);
    280         mPhoneStateListener.onDataConnectionStateChanged(dataState, dataNetType);
    281     }
    282 
    283     public void updateDataActivity(int dataActivity) {
    284         mPhoneStateListener.onDataActivity(dataActivity);
    285     }
    286 
    287     public void setCarrierNetworkChange(boolean enable) {
    288         Log.d(TAG, "setCarrierNetworkChange(" + enable + ")");
    289         mPhoneStateListener.onCarrierNetworkChange(enable);
    290     }
    291 
    292     protected void verifyHasNoSims(boolean hasNoSimsVisible) {
    293         Mockito.verify(mCallbackHandler, Mockito.atLeastOnce()).setNoSims(
    294                 eq(hasNoSimsVisible), eq(false));
    295     }
    296 
    297     protected void verifyLastQsMobileDataIndicators(boolean visible, int icon, int typeIcon,
    298             boolean dataIn, boolean dataOut) {
    299         ArgumentCaptor<IconState> iconArg = ArgumentCaptor.forClass(IconState.class);
    300         ArgumentCaptor<Integer> typeIconArg = ArgumentCaptor.forClass(Integer.class);
    301         ArgumentCaptor<Boolean> dataInArg = ArgumentCaptor.forClass(Boolean.class);
    302         ArgumentCaptor<Boolean> dataOutArg = ArgumentCaptor.forClass(Boolean.class);
    303 
    304         Mockito.verify(mCallbackHandler, Mockito.atLeastOnce()).setMobileDataIndicators(
    305                     any(),
    306                     iconArg.capture(),
    307                     anyInt(),
    308                     typeIconArg.capture(), dataInArg.capture(), dataOutArg.capture(),
    309                     anyString(), anyString(), anyBoolean(), anyInt(), anyBoolean());
    310         IconState iconState = iconArg.getValue();
    311         int state = SignalDrawable.getState(icon, SignalStrength.NUM_SIGNAL_STRENGTH_BINS,
    312                 false);
    313         assertEquals("Visibility in, quick settings", visible, iconState.visible);
    314         assertEquals("Signal icon in, quick settings", state, iconState.icon);
    315         assertEquals("Data icon in, quick settings", typeIcon, (int) typeIconArg.getValue());
    316         assertEquals("Data direction in, in quick settings", dataIn,
    317                 (boolean) dataInArg.getValue());
    318         assertEquals("Data direction out, in quick settings", dataOut,
    319                 (boolean) dataOutArg.getValue());
    320     }
    321 
    322     protected void verifyLastMobileDataIndicators(boolean visible, int icon, int typeIcon) {
    323         verifyLastMobileDataIndicators(visible, icon, typeIcon, false);
    324     }
    325 
    326     protected void verifyLastMobileDataIndicators(boolean visible, int icon, int typeIcon,
    327             boolean roaming) {
    328         verifyLastMobileDataIndicators(visible, icon, typeIcon, roaming, true);
    329     }
    330 
    331     protected void verifyLastMobileDataIndicators(boolean visible, int icon, int typeIcon,
    332         boolean roaming, boolean inet) {
    333         ArgumentCaptor<IconState> iconArg = ArgumentCaptor.forClass(IconState.class);
    334         ArgumentCaptor<Integer> typeIconArg = ArgumentCaptor.forClass(Integer.class);
    335 
    336         // TODO: Verify all fields.
    337         Mockito.verify(mCallbackHandler, Mockito.atLeastOnce()).setMobileDataIndicators(
    338                 iconArg.capture(),
    339                 any(),
    340                 typeIconArg.capture(),
    341                 anyInt(), anyBoolean(), anyBoolean(), anyString(), anyString(), anyBoolean(),
    342                 anyInt(), eq(roaming));
    343         IconState iconState = iconArg.getValue();
    344 
    345         int state = icon == -1 ? 0
    346                 : SignalDrawable.getState(icon, SignalStrength.NUM_SIGNAL_STRENGTH_BINS, !inet);
    347         assertEquals("Signal icon in status bar", state, iconState.icon);
    348         assertEquals("Data icon in status bar", typeIcon, (int) typeIconArg.getValue());
    349         assertEquals("Visibility in status bar", visible, iconState.visible);
    350     }
    351 
    352     protected void verifyLastMobileDataIndicators(boolean visible, int icon, int typeIcon,
    353             boolean qsVisible, int qsIcon, int qsTypeIcon, boolean dataIn, boolean dataOut) {
    354         ArgumentCaptor<IconState> iconArg = ArgumentCaptor.forClass(IconState.class);
    355         ArgumentCaptor<Integer> typeIconArg = ArgumentCaptor.forClass(Integer.class);
    356         ArgumentCaptor<IconState> qsIconArg = ArgumentCaptor.forClass(IconState.class);
    357         ArgumentCaptor<Integer> qsTypeIconArg = ArgumentCaptor.forClass(Integer.class);
    358         ArgumentCaptor<Boolean> dataInArg = ArgumentCaptor.forClass(Boolean.class);
    359         ArgumentCaptor<Boolean> dataOutArg = ArgumentCaptor.forClass(Boolean.class);
    360 
    361         Mockito.verify(mCallbackHandler, Mockito.atLeastOnce()).setMobileDataIndicators(
    362                 iconArg.capture(),
    363                 qsIconArg.capture(),
    364                 typeIconArg.capture(),
    365                 qsTypeIconArg.capture(),
    366                 dataInArg.capture(),
    367                 dataOutArg.capture(),
    368                 anyString(), anyString(), anyBoolean(), anyInt(), anyBoolean());
    369 
    370         IconState iconState = iconArg.getValue();
    371 
    372         int state = SignalDrawable.getState(icon, SignalStrength.NUM_SIGNAL_STRENGTH_BINS,
    373                 false);
    374         assertEquals("Data icon in status bar", typeIcon, (int) typeIconArg.getValue());
    375         assertEquals("Signal icon in status bar", state, iconState.icon);
    376         assertEquals("Visibility in status bar", visible, iconState.visible);
    377 
    378         iconState = qsIconArg.getValue();
    379         assertEquals("Visibility in quick settings", qsVisible, iconState.visible);
    380         assertEquals("Signal icon in quick settings", state, iconState.icon);
    381         assertEquals("Data icon in quick settings", qsTypeIcon, (int) qsTypeIconArg.getValue());
    382         assertEquals("Data direction in in quick settings", dataIn,
    383                 (boolean) dataInArg.getValue());
    384         assertEquals("Data direction out in quick settings", dataOut,
    385                 (boolean) dataOutArg.getValue());
    386     }
    387 
    388    protected void assertNetworkNameEquals(String expected) {
    389        assertEquals("Network name", expected, mMobileSignalController.getState().networkName);
    390    }
    391 }
    392